2012-03-17 5 views
5

¿Alguien ha encontrado una forma de interceptar los formularios predeterminados Form :: postLink() con Jquery? Me gustaría que el formulario funcione sin JS (por lo tanto, el postLink). Pero con JS habilitado, quiero interceptar la publicación y llamarla a través de AJAX.Interceptar cake2 postLink() mensajes con jQuery

<?php echo $this->Form->postLink('Delete', array('action'=>'delete', $prospect['Prospect']['id']), array('class'=>'postLink', 'escape'=>false), __('Sure you want to delete # %s?', $prospect['Prospect']['id'])); ?> 

genera:

<form action="/admin/prospects/delete/4f61ce95-2b6c-4009-9b89-07e852b0caef" name="post_4f648f773923b" id="post_4f648f773923b" style="display:none;" method="post"> 
    <input type="hidden" name="_method" value="POST"/> 
</form> 
<a href="#" class="postLink" onclick="if (confirm('Sure you want to delete # 4f61ce95-2b6c-4009-9b89-07e852b0caef?')) { document.post_4f648f773923b.submit(); } event.returnValue = false; return false;"> 
    Delete 
</a> 

El problema principal es que el js se coloca en línea aquí. Por lo tanto, siempre se activa el incluso si intento para interceptar el evento click (o el post evento - intentó que también):

<script> 
$(document).ready(function() { 
    $('table.list a.postLink').click(function(e) { 
     e.preventDefault(); 
     alert('Handler for .submit() called.'); 
     // TODO: do ajax request here and return false 
     return false; 
    }); 
}); 
</script> 

Así que al final la forma siempre se somete normalmente y redirige - ya sea haciendo caso omiso de cualquier llamada AJAX (para controlar el envío de formulario) o publicación/redirección independientemente de una llamada ajax recién realizada (capturando el evento click).

Me gustaría eliminar este registro a través de AJAX y, si tiene éxito, simplemente elimine esa fila de la tabla de DOM. Sin embargo, sería genial si uno no tiene que modificar los más de 300 "botones de eliminación" en la aplicación.

Si todo falla, es probable que aún pueda anular el FormHelper (extenderlo y alias). Pero esperaba una solución menos invasiva aquí.

Respuesta

8

Sé que esto es viejo, pero para cualquiera de los que buscan:

  • Es necesario eliminar primero el atributo 'onclick' agregado al enlace eliminar .
  • A continuación, agregar una función a la .click enlace borrar
  • Se necesita el URL (que puede ser codificado o se recupera de la forma, que es siempre el elemento anterior en cakephp form-> postLink

aquí está el código:


$(function(){ 

    $('a:contains("Delete")').removeAttr('onclick'); 

    $('a:contains("Delete")').click(function(e){ 
     e.preventDefault(); 
     var form = $(this).prev(); 
     url = $(form).attr("action"); 
     $.post(url); 
     return false; 
    }); 

}); 
+0

Quitar el atributo 'onclick' era lo que me faltaba. Bueno, gracias! – nIcO

0

Sólo una idea, no lo he probado:

<?php echo $this->Form->postLink('Delete', array('action'=>'delete', $prospect['Prospect']['id']), array('class'=>'postLink', 'onclick' => false, 'escape'=>false), __('Sure you want to delete # %s?', $prospect['Prospect']['id'])); ?> 
+0

pero entonces tendría que alterar todos los más de 300 puntos de vista donde se producen los enlaces :) probablemente tengo que usar mi propio asistente de formulario aquí, que sobrescribe s el js sale en línea ... – mark

+1

Acabo de probar esto. No funciona El evento onclick aún se agrega. –

2

jymboche - lo que un genio por qué aún no ha pienso en mí mismo

Bueno, aquí es el Answ modificado? de los suyos:

$(document).ready(function() { 
    $('table.list a.postLink').removeAttr('onclick'); 

    $('table.list a.postLink').click(function(e) { 
     e.preventDefault(); 
     if (!confirm('<?php echo __('Sure?')?>')) { 
      return false; 
     } 
     var form = $(this).prev(); 
     var url = $(form).attr("action"); 
     var tr = $(this).closest('tr'); 
     url = url + '.json'; 
     $.post(url).success(function(res) { 
      if (res.error) { 
       alert(res.error); 
       return false; 
      } 
      tr.fadeOut(200); 
     }).error(function() { 
      alert("Error"); 
     }) 
     return false; 
    }); 
}); 

Esto es solo para referencia futura. Aún aceptaré su respuesta ya que me dio la idea correcta.

0

par de problemas con las soluciones actuales ...

En primer lugar, el método postLink requiere que Javascript esté habilitado. De Cake's doco: "Crea un enlace HTML, pero accede a la url usando el método POST. Requiere javascript para habilitarse en el navegador".

Si javascript está deshabilitado, obtiene exactamente el mismo resultado, un formulario oculto y un enlace que intenta enviar ese formulario con Javascript (pero falla, ya que JS está desactivado).

En segundo lugar, aunque funcionará, parece extraño usar el método postLink, y luego usar Javacript para deshacer con precisión toda la magia que crea el método postLink.

Si desea una solución amistosa no javascript, todo lo que tiene que hacer es crear una forma regular que apunta al método de eliminación, y poner un enlace a continuación de esta manera:

<?php echo $this->Form->create('DefaultAvailability', array('url' array('action' => 'delete', $myRecord['ModelName']['id'])));?> 
<?php echo $this->Form->end('Delete (no JS)');?> 
<a href='#'>Delete (With JS, use AJAX)</a> 

Entonces, por En los casos en que no hay javascript, oculte el siguiente enlace y el formulario funcionará normalmente.

Para los casos en que haya javascript, oculte el formulario y use javascript para hacer que su enlace de eliminación active un envío en su formulario de eliminación, y maneje ese envío con ajax.

1

La solución de jymboche me ayudó a obtener una respuesta funcional, pero no funcionó completamente para mí, debido a algunos complementos de seguridad que he instalado.

Esto es lo que funcionó para mí:

$(function(){ 

    $('a:contains("Delete")').removeAttr('onclick'); 

    $('a:contains("Delete")').click(function(e){ 

     e.preventDefault(); 
     var form = $(this).prev(); 
     var url = $(form).attr("action"); 

     $.ajax({ 
      type: 'POST', 
      cache: false, 
      url: url, 
      data: $(form).serialize(), 
      success: function(msg) { 
       // do any extra calls you need to refresh the page 
      } 
     }); 
     return false; 
    }); 

}); 
0

He traducido la versión anterior jQuery para Mootools

// Comenzamos con foreach, para seleccionar todos los botones de la página ajax $$ ('.ajaxbutton'). cada uno (función (artículo, índice) {

 //remove onClick 
     item.removeProperty('onclick'); 

     //attach click event 
     item.addEvent('click', function(e){ 
      //stop click (in my case the form is inside another link) 
      e.stop(); 
      var form = item.getPrevious(); 
      url = form.get('action'); 

      new Request({ 
       url: url,//url 
       method: 'post',//method 
       onSuccess: function(responseText){ 
        //This is not required, we are dimming the button on success 
        item.getParents()[0].tween('opacity',0.5) 
       } 
      }).send(); 
      return false; 
     }); 

    }) 
Cuestiones relacionadas