<?php
include_once $_SERVER['DOCUMENT_ROOT'] . '/include/shared-manual.inc';
$TOC = array();
$TOC_DEPRECATED = array();
$PARENTS = array();
include_once dirname(__FILE__) ."/toc/ref.exec.inc";
$setup = array (
  'home' => 
  array (
    0 => 'index.php',
    1 => 'PHP Manual',
  ),
  'head' => 
  array (
    0 => 'UTF-8',
    1 => 'es',
  ),
  'this' => 
  array (
    0 => 'function.proc-open.php',
    1 => 'proc_open',
    2 => 'Ejecuta un comando y abre los punteros de ficheros para las entradas / salidas',
  ),
  'up' => 
  array (
    0 => 'ref.exec.php',
    1 => 'Funciones de ejecuci&oacute;n de programas',
  ),
  'prev' => 
  array (
    0 => 'function.proc-nice.php',
    1 => 'proc_nice',
  ),
  'next' => 
  array (
    0 => 'function.proc-terminate.php',
    1 => 'proc_terminate',
  ),
  'alternatives' => 
  array (
  ),
  'source' => 
  array (
    'lang' => 'es',
    'path' => 'reference/exec/functions/proc-open.xml',
  ),
  'history' => 
  array (
  ),
);
$setup["toc"] = $TOC;
$setup["toc_deprecated"] = $TOC_DEPRECATED;
$setup["parents"] = $PARENTS;
manual_setup($setup);

contributors($setup);

?>
<div id="function.proc-open" class="refentry">
 <div class="refnamediv">
  <h1 class="refname">proc_open</h1>
  <p class="verinfo">(PHP 4 &gt;= 4.3.0, PHP 5, PHP 7, PHP 8)</p><p class="refpurpose"><span class="refname">proc_open</span> &mdash; <span class="dc-title">
   Ejecuta un comando y abre los punteros de ficheros para las entradas / salidas
  </span></p>

 </div>
 <div class="refsect1 description" id="refsect1-function.proc-open-description">
  <h3 class="title">Descripción</h3>
  <div class="methodsynopsis dc-description">
   <span class="methodname"><strong>proc_open</strong></span>(<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><span class="type"><a href="language.types.array.php" class="type array">array</a></span>|<span class="type"><a href="language.types.string.php" class="type string">string</a></span></span> <code class="parameter">$command</code></span>,<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><a href="language.types.array.php" class="type array">array</a></span> <code class="parameter">$descriptor_spec</code></span>,<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><a href="language.types.array.php" class="type array">array</a></span> <code class="parameter reference">&$pipes</code></span>,<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><span class="type"><a href="language.types.null.php" class="type null">?</a></span><span class="type"><a href="language.types.string.php" class="type string">string</a></span></span> <code class="parameter">$cwd</code><span class="initializer"> = <strong><code><a href="reserved.constants.php#constant.null">null</a></code></strong></span></span>,<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><span class="type"><a href="language.types.null.php" class="type null">?</a></span><span class="type"><a href="language.types.array.php" class="type array">array</a></span></span> <code class="parameter">$env_vars</code><span class="initializer"> = <strong><code><a href="reserved.constants.php#constant.null">null</a></code></strong></span></span>,<br>&nbsp;&nbsp;&nbsp;&nbsp;<span class="methodparam"><span class="type"><span class="type"><a href="language.types.null.php" class="type null">?</a></span><span class="type"><a href="language.types.array.php" class="type array">array</a></span></span> <code class="parameter">$options</code><span class="initializer"> = <strong><code><a href="reserved.constants.php#constant.null">null</a></code></strong></span></span><br>): <span class="type"><span class="type"><a href="language.types.resource.php" class="type resource">resource</a></span>|<span class="type"><a href="language.types.singleton.php" class="type false">false</a></span></span></div>

  <p class="para rdfs-comment">
   <span class="function"><strong>proc_open()</strong></span> es similar a <span class="function"><a href="function.popen.php" class="function">popen()</a></span>
   pero proporciona un mayor grado de control sobre la ejecución del programa.
  </p>
 </div>

 <div class="refsect1 parameters" id="refsect1-function.proc-open-parameters">
  <h3 class="title">Parámetros</h3>
  <p class="para">
   <dl>
    
     <dt><code class="parameter">command</code></dt>
     <dd>
      <p class="para">
       El comando a ejecutar como <span class="type"><a href="language.types.string.php" class="type string">string</a></span>. Los caracteres especiales
       deben ser escapados correctamente, y una aplicación correcta de
       las comillas debe ser aplicada.
      </p>
      <blockquote class="note"><p><strong class="note">Nota</strong>: 
       <span class="simpara">
        En <em>Windows</em>, a menos que <code class="literal">bypass_shell</code> esté definida a <strong><code><a href="reserved.constants.php#constant.true">true</a></code></strong> en
        <code class="parameter">options</code>, <code class="parameter">command</code> es
        pasado a <strong class="command">cmd.exe</strong> (en realidad, <code class="literal">%ComSpec%</code>)
        con el flag <code class="literal">/c</code> como un <span class="type"><a href="language.types.string.php" class="type string">string</a></span> <em>sin
        comillas</em> (es decir, exactamente como fue proporcionado a
        <span class="function"><strong>proc_open()</strong></span>). Esto puede causar
        <strong class="command">cmd.exe</strong> para eliminar las comillas que rodean
        <code class="parameter">command</code> (para más detalles ver la documentación
        de <strong class="command">cmd.exe</strong>), resultando en un comportamiento
        inesperado, y potencialmente peligroso, ya que los mensajes de error de
        <strong class="command">cmd.exe</strong> pueden contener (una parte de) la
        <code class="parameter">command</code> pasada (ver ejemplo a continuación).
       </span>
      </p></blockquote>
      <p class="para">
       A partir de PHP 7.4.0, <code class="parameter">command</code> puede ser pasado como
       un <span class="type"><a href="language.types.array.php" class="type array">array</a></span> de argumentos de comandos.
       En este caso el proceso será abierto directamente (sin pasar por un shell) y PHP se encargará de escapar los argumentos necesarios.
      </p>
      <blockquote class="note"><p><strong class="note">Nota</strong>: 
       <p class="para">
        En Windows, el escape de los argumentos de los elementos del <span class="type"><a href="language.types.array.php" class="type array">array</a></span> asume
        que el procesamiento de la línea de comandos del comando ejecutado es
        compatible con el procesamiento de argumentos de línea de comandos realizado por el runtime VC.
       </p>
      </p></blockquote>
     </dd>
    
    
     <dt><code class="parameter">descriptor_spec</code></dt>
     <dd>
      <p class="para">
       Un array indexado, donde las claves representan el número de descriptor
       y el valor el método con el cual PHP pasará este descriptor al
       proceso hijo. 0 es stdin, 1 es stdout, y 2 es stderr.
      </p>
      <p class="para">
       Cada elemento puede ser:
       <ul class="simplelist">
        <li>
         Un array que describe el pipe a pasar al proceso. El primer elemento
         es el tipo del descriptor y el segundo es una opción para el tipo dado.
         Los tipos válidos son <code class="literal">pipe</code> (el segundo elemento es
         <code class="literal">r</code> para pasar el extremo de lectura del pipe al proceso, o
         <code class="literal">w</code> para pasar el extremo de escritura) y
         <code class="literal">file</code> (el segundo elemento es el nombre de fichero).
         Se debe notar que cualquier otro elemento diferente de <code class="literal">w</code> es tratado como <code class="literal">r</code>.
        </li>
        <li>
         Un recurso de flujo que representa un descriptor de fichero (por ejemplo, un fichero
         abierto, un socket, o bien <strong><code><a href="reserved.constants.php#constant.stdin">STDIN</a></code></strong>).
        </li>
       </ul>
      </p>
      <p class="para">
       Los números de punteros de ficheros no están limitados a 0, 1 y 2 -
       se puede especificar cualquier número de descriptor válido, y
       será pasado al proceso hijo. Esto permitirá que su script interactúe
       con otros scripts, y que sea ejecutado como &quot;co-proceso&quot;. En particular,
       es muy práctico para pasar contraseñas a programas como
       PGP, GPG y openssl, con un método muy protegido. También es práctico
       para leer información de estado proporcionada por estos programas, en
       descriptores auxiliares.
      </p>
     </dd>
    
    
     <dt><code class="parameter">pipes</code></dt>
     <dd>
      <p class="para">
       Debe ser definido como un array indexado de punteros de ficheros que
       corresponden al extremo de cualquier descriptor PHP que sean
       creados.
      </p>
     </dd>
    
    
     <dt><code class="parameter">cwd</code></dt>
     <dd>
      <p class="para">
       El directorio inicial de trabajo del comando. Esto debe ser
       una ruta <strong>absoluta</strong>
       al directorio o <strong><code><a href="reserved.constants.php#constant.null">null</a></code></strong> si se quiere utilizar el valor
       por omisión (el directorio de trabajo del proceso PHP actual)
      </p>
     </dd>
    
    
     <dt><code class="parameter">env_vars</code></dt>
     <dd>
      <p class="para">
       Un array que contiene las variables de entorno para el comando
       que debe ser ejecutado, o <strong><code><a href="reserved.constants.php#constant.null">null</a></code></strong> para utilizar el mismo entorno
       que el proceso PHP actual
      </p>
     </dd>
    
    
     <dt><code class="parameter">options</code></dt>
     <dd>
      <p class="para">
       Permite especificar opciones adicionales. Las opciones
       actualmente soportadas son:
       <ul class="simplelist">
        <li>
         <code class="literal">suppress_errors</code> (solo Windows): supresión de
         errores generados por esta función cuando está definida a <strong><code><a href="reserved.constants.php#constant.true">true</a></code></strong>
        </li>
        <li>
         <code class="literal">bypass_shell</code> (solo Windows): omisión del shell
         <code class="literal">cmd.exe</code> cuando está definida a <strong><code><a href="reserved.constants.php#constant.true">true</a></code></strong>
        </li>
        <li>
         <code class="literal">blocking_pipes</code> (solo Windows): fuerza
         los pipes bloqueantes cuando está definida a <strong><code><a href="reserved.constants.php#constant.true">true</a></code></strong>
        </li>
        <li>
         <code class="literal">create_process_group</code> (solo Windows): permite
         al proceso hijo manejar los eventos <code class="literal">CTRL</code>
         cuando está a <strong><code><a href="reserved.constants.php#constant.true">true</a></code></strong>
        </li>
        <li>
         <code class="literal">create_new_console</code> (solo Windows): el nuevo
         proceso tiene una nueva consola, en lugar de heredar la consola de su
         padre.
        </li>
       </ul>
      </p>
     </dd>
    
   </dl>
  </p>
 </div>

 <div class="refsect1 returnvalues" id="refsect1-function.proc-open-returnvalues">
  <h3 class="title">Valores devueltos</h3>
  <p class="para">
   Retorna un recurso que representa el proceso, que podrá ser utilizado por
   la función <span class="function"><a href="function.proc-close.php" class="function">proc_close()</a></span> cuando ya no sea necesario.
   En caso de fallo, <strong><code><a href="reserved.constants.php#constant.false">false</a></code></strong> será retornado.
  </p>
 </div>


 <div class="refsect1 errors" id="refsect1-function.proc-open-errors">
  <h3 class="title">Errores/Excepciones</h3>
  <p class="simpara">
   A partir de PHP 8.3.0, se lanza una excepción <span class="exceptionname"><a href="class.valueerror.php" class="exceptionname">ValueError</a></span> si
   <code class="parameter">command</code> es un array sin al menos un elemento no vacío.
  </p>
 </div>


 <div class="refsect1 changelog" id="refsect1-function.proc-open-changelog">
  <h3 class="title">Historial de cambios</h3>
  <p class="para">
   <table class="doctable informaltable">
    
     <thead>
      <tr>
       <th>Versión</th>
       <th>Descripción</th>
      </tr>

     </thead>

     <tbody class="tbody">
      <tr>
       <td>8.3.0</td>
       <td>
        Se lanzará una excepción <span class="exceptionname"><a href="class.valueerror.php" class="exceptionname">ValueError</a></span> si
        <code class="parameter">command</code> es un array sin al menos un elemento no vacío.
       </td>
      </tr>

      <tr>
       <td>7.4.4</td>
       <td>
        Se añadió la opción <code class="literal">create_new_console</code> al parámetro
        <code class="parameter">options</code>.
       </td>
      </tr>

      <tr>
       <td>7.4.0</td>
       <td>
        <span class="function"><strong>proc_open()</strong></span> ahora acepta un <span class="type"><a href="language.types.array.php" class="type array">array</a></span>
        para <code class="parameter">command</code>.
       </td>
      </tr>

      <tr>
       <td>7.4.0</td>
       <td>
        Se añadió la opción <code class="literal">create_process_group</code> al parámetro
        <code class="parameter">options</code>.
       </td>
      </tr>

     </tbody>
    
   </table>

  </p>
 </div>

 <div class="refsect1 examples" id="refsect1-function.proc-open-examples">
  <h3 class="title">Ejemplos</h3>
  <p class="para">
   <div class="example" id="example-1">
    <p><strong>Ejemplo #1 Ejemplo con <span class="function"><strong>proc_open()</strong></span></strong></p>
    <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />$descriptorspec </span><span style="color: #007700">= array(<br />   </span><span style="color: #0000BB">0 </span><span style="color: #007700">=&gt; array(</span><span style="color: #DD0000">"pipe"</span><span style="color: #007700">, </span><span style="color: #DD0000">"r"</span><span style="color: #007700">),  </span><span style="color: #FF8000">// stdin es un pipe donde el proceso leerá<br />   </span><span style="color: #0000BB">1 </span><span style="color: #007700">=&gt; array(</span><span style="color: #DD0000">"pipe"</span><span style="color: #007700">, </span><span style="color: #DD0000">"w"</span><span style="color: #007700">),  </span><span style="color: #FF8000">// stdout es un pipe donde el proceso escribirá<br />   </span><span style="color: #0000BB">2 </span><span style="color: #007700">=&gt; array(</span><span style="color: #DD0000">"file"</span><span style="color: #007700">, </span><span style="color: #DD0000">"/tmp/error-output.txt"</span><span style="color: #007700">, </span><span style="color: #DD0000">"a"</span><span style="color: #007700">) </span><span style="color: #FF8000">// stderr es un fichero<br /></span><span style="color: #007700">);<br /><br /></span><span style="color: #0000BB">$cwd </span><span style="color: #007700">= </span><span style="color: #DD0000">'/tmp'</span><span style="color: #007700">;<br /></span><span style="color: #0000BB">$env </span><span style="color: #007700">= array(</span><span style="color: #DD0000">'some_option' </span><span style="color: #007700">=&gt; </span><span style="color: #DD0000">'aeiou'</span><span style="color: #007700">);<br /><br /></span><span style="color: #0000BB">$process </span><span style="color: #007700">= </span><span style="color: #0000BB">proc_open</span><span style="color: #007700">(</span><span style="color: #DD0000">'php'</span><span style="color: #007700">, </span><span style="color: #0000BB">$descriptorspec</span><span style="color: #007700">, </span><span style="color: #0000BB">$pipes</span><span style="color: #007700">, </span><span style="color: #0000BB">$cwd</span><span style="color: #007700">, </span><span style="color: #0000BB">$env</span><span style="color: #007700">);<br /><br />if (</span><span style="color: #0000BB">is_resource</span><span style="color: #007700">(</span><span style="color: #0000BB">$process</span><span style="color: #007700">)) {<br />    </span><span style="color: #FF8000">// $pipes se parece a:<br />    // 0 =&gt; fichero accesible en escritura, conectado a la entrada estándar del proceso hijo<br />    // 1 =&gt; fichero accesible en lectura, conectado a la salida estándar del proceso hijo<br />    // Cualquier error será añadido al fichero /tmp/error-output.txt<br /><br />    </span><span style="color: #0000BB">fwrite</span><span style="color: #007700">(</span><span style="color: #0000BB">$pipes</span><span style="color: #007700">[</span><span style="color: #0000BB">0</span><span style="color: #007700">], </span><span style="color: #DD0000">'&lt;?php print_r($_ENV); ?&gt;'</span><span style="color: #007700">);<br />    </span><span style="color: #0000BB">fclose</span><span style="color: #007700">(</span><span style="color: #0000BB">$pipes</span><span style="color: #007700">[</span><span style="color: #0000BB">0</span><span style="color: #007700">]);<br /><br />    echo </span><span style="color: #0000BB">stream_get_contents</span><span style="color: #007700">(</span><span style="color: #0000BB">$pipes</span><span style="color: #007700">[</span><span style="color: #0000BB">1</span><span style="color: #007700">]);<br />    </span><span style="color: #0000BB">fclose</span><span style="color: #007700">(</span><span style="color: #0000BB">$pipes</span><span style="color: #007700">[</span><span style="color: #0000BB">1</span><span style="color: #007700">]);<br /><br />    </span><span style="color: #FF8000">// Es importante que cierre los pipes antes de llamar<br />    // a proc_close para evitar un bloqueo.<br />    </span><span style="color: #0000BB">$return_value </span><span style="color: #007700">= </span><span style="color: #0000BB">proc_close</span><span style="color: #007700">(</span><span style="color: #0000BB">$process</span><span style="color: #007700">);<br /><br />    echo </span><span style="color: #DD0000">"El comando retornó </span><span style="color: #0000BB">$return_value</span><span style="color: #DD0000">\n"</span><span style="color: #007700">;<br />}<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
    </div>

    <div class="example-contents"><p>Resultado del ejemplo anterior es similar a:</p></div>
    <div class="example-contents screen">
<div class="examplescode"><pre class="examplescode">Array
(
    [some_option] =&gt; aeiou
    [PWD] =&gt; /tmp
    [SHLVL] =&gt; 1
    [_] =&gt; /usr/local/bin/php
)
El comando retornó 0</pre>
</div>
    </div>
   </div>
  </p>
  <p class="para">
   <div class="example" id="example-2">
    <p><strong>Ejemplo #2 Comportamiento extraño de <span class="function"><strong>proc_open()</strong></span> en Windows</strong></p>
    <div class="example-contents"><p>
     Aunque se podría esperar que el siguiente programa busque
     el fichero <var class="filename">filename.txt</var> para el texto
     <code class="literal">search</code> y muestre los resultados,
     se comporta de manera diferente.
    </p></div>
    <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000"><span style="color: #0000BB">&lt;?php<br />$descriptorspec </span><span style="color: #007700">= [</span><span style="color: #0000BB">STDIN</span><span style="color: #007700">, </span><span style="color: #0000BB">STDOUT</span><span style="color: #007700">, </span><span style="color: #0000BB">STDOUT</span><span style="color: #007700">];<br /></span><span style="color: #0000BB">$cmd </span><span style="color: #007700">= </span><span style="color: #DD0000">'"findstr" "search" "filename.txt"'</span><span style="color: #007700">;<br /></span><span style="color: #0000BB">$proc </span><span style="color: #007700">= </span><span style="color: #0000BB">proc_open</span><span style="color: #007700">(</span><span style="color: #0000BB">$cmd</span><span style="color: #007700">, </span><span style="color: #0000BB">$descriptorspec</span><span style="color: #007700">, </span><span style="color: #0000BB">$pipes</span><span style="color: #007700">);<br /></span><span style="color: #0000BB">proc_close</span><span style="color: #007700">(</span><span style="color: #0000BB">$proc</span><span style="color: #007700">);<br /></span><span style="color: #0000BB">?&gt;</span></span></code></div>
    </div>

    <div class="example-contents"><p>El ejemplo anterior mostrará:</p></div>
    <div class="example-contents screen">
<div class="examplescode"><pre class="examplescode">&#039;findstr&quot; &quot;search&quot; &quot;filename.txt&#039; no se reconoce como un comando interno o externo,
programa ejecutable o archivo por lotes.</pre>
</div>
    </div>
    <div class="example-contents"><p>
     Para evitar este comportamiento, generalmente es suficiente rodear
     <code class="parameter">command</code> con comillas adicionales:
    </p></div>
    <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000">$cmd = '""findstr" "search" "filename.txt""';</span></code></div>
    </div>

   </div>
  </p>
 </div>

 <div class="refsect1 notes" id="refsect1-function.proc-open-notes">
  <h3 class="title">Notas</h3>
  <blockquote class="note"><p><strong class="note">Nota</strong>: 
   <p class="para">
    Compatibilidad Windows: los descriptores más allá de 2 (stderr) son
    accesibles al proceso hijo, en forma de punteros heredados, pero
    como la arquitectura Windows no asocia números a los descriptores
    de bajo nivel, el proceso hijo no tiene, actualmente, ningún medio
    para acceder a ellos. Por otro lado, stdin, stdout y stderr funcionan
    como de costumbre.
   </p>
  </p></blockquote>
  <blockquote class="note"><p><strong class="note">Nota</strong>: 
   <p class="para">
    Si solo se necesita un proceso unidireccional,
    <span class="function"><a href="function.popen.php" class="function">popen()</a></span> será más práctico, ya que es más
    sencillo de utilizar.
   </p>
  </p></blockquote>
 </div>

 <div class="refsect1 seealso" id="refsect1-function.proc-open-seealso">
  <h3 class="title">Ver también</h3>
  <p class="para">
   <ul class="simplelist">
    <li><span class="function"><a href="function.popen.php" class="function" rel="rdfs-seeAlso">popen()</a> - Crea un puntero de archivo de proceso</span></li>
    <li><span class="function"><a href="function.exec.php" class="function" rel="rdfs-seeAlso">exec()</a> - Ejecuta un programa externo</span></li>
    <li><span class="function"><a href="function.system.php" class="function" rel="rdfs-seeAlso">system()</a> - Ejecutar un programa externo y mostrar su salida</span></li>
    <li><span class="function"><a href="function.passthru.php" class="function" rel="rdfs-seeAlso">passthru()</a> - Ejecuta un programa externo y muestra el resultado sin procesar</span></li>
    <li><span class="function"><a href="function.stream-select.php" class="function" rel="rdfs-seeAlso">stream_select()</a> - Supervisa la modificaci&oacute;n de uno o varios flujos</span></li>
    <li><a href="language.operators.execution.php" class="link">Las comillas invertidas</a></li>
   </ul>
  </p>
 </div>

</div><?php manual_footer($setup); ?>