2010-12-09 7 views
0

je veux rendre une action d'un autre contrôleur, mais je reçois l'erreur:Rails3 rendu l'action d'un autre contrôleur

méthode non définie formats' pour nil: NilClass

<script> 
$("#validate_company").live("keyup", function() { 
$("#company_info").html("<%= escape_javascript(render(:controller => 'live_validation', :action => 'validate_client_company')) %>"); 
}); 
</script> 

Ceci est le contrôleur:

class LiveValidationsController < ApplicationController 

def validate_client_company 
    if params[:first_name].length > 0 
    @client = Client.find_by_company(params[:company]) 
    if @client.nil? 
     @message = "<img src='/images/accepted_48.png' alt='Valid Username'/>" 
    else 
     @message = "<img src='/images/cancel_48.png' alt='Invalid Username' /> Name taken" 
    end 
    else 
    @message = "" 
    end 
    render :partial => "message" 
end 

end 

La _message partielle est juste

<%= @message %> 
+0

poster votre "message" partiel et pourquoi rendre partiel du contrôleur? – Bohdan

Répondre

2

Vous semblez mélanger des choses.

Vous avez html dans votre contrôleur-méthode? Cela devrait être à votre avis. Pour chaque méthode de contrôleur, normalement une vue avec le même nom est affichée, sauf si vous appelez explicitement render à partir de votre méthode de contrôleur.

Vous n'écrivez pas html dans votre contrôleur. Vous écrivez html dans la vue, et parfois vous avez des aides pour rendre vos vues plus lisibles. Deuxièmement, dans votre premier morceau de code, qui est un code de vue, j'espère. La vue est préparée côté serveur, puis envoyée au client. Vous pouvez afficher une autre vue, partielle, à partir d'une vue. Mais cela ne charge pas les données en direct.

Comment je voudrais résoudre ce problème.A l'intérieur de vos vues où vous voulez rendre dynamiquement la validation:

<script> 
    $("#validate_company").live("keyup", function() { 
    $("#company_info").load("<%= url_for :controller => 'live_validations', :action => 'validate_client_company' %>"); 
    }); 
</script> 

Ensuite, l'intérieur de votre contrôleur, vous écrivez:

class LiveValidationsController < ApplicationController 

    def validate_client_company 
    if params[:first_name].length > 0 
     @client = Client.find_by_company(params[:company]) 
     @error = @client.nil? ? :valid_username : :invalid_username 
    else 
     @error = nil 
    end 
    render :partial => "message", :layout => false 
    end 

end 

l'intérieur de votre app/helper/live_validations_helper.rb vous ajoutez une méthode

def get_validation_message(error) 
    if error == :invalid_username 
    image_tag('/images/cancel_48.png', :alt => 'Invalid Username') + "Name taken" 
    elsif error == :valid_username 
    image_tag('/images/accepted_48.png', :alt => 'Valid Username') 
    end 
end 

et à l'intérieur de votre message voir vous écrivez quelque chose comme:

<%= get_validation_message(@error) %> 
+0

merci! le script est dans app/views/clients/new.html.erb, mais il ne rend pas dynamiquement la validation. <% = url_for: controller => 'live_validations',: action => 'validate_client_company' %> est \t "/ live_validations/validate_client_company" et quand je navigue à «/live_validations/validate_client_company entreprise = testnames? "il rend la validation correcte. – max

+0

Vous devrez envoyer le paramètre. Est-ce corrigé? Ou doit-il provenir de l'entrée? Quel sélecteur est-ce? Vous pouvez envoyer des variables dans la méthode 'load' de jquery. – nathanvda

2

render :action => ne pas exécuter la méthode de contrôleur associé.

Il rend simplement le modèle que Rails aurait, par défaut, associé à l'action. C'est-à-dire, si l'action validate_client_company simplement appelée render sans passer aucun argument, Rails rechercherait un modèle dans un dossier avec le même nom que le contrôleur et avec un nom avec le même nom que l'action. Appeler render :action => recherche simplement le même modèle et le restitue.

La meilleure estimation est que Rails ne peut pas trouver un modèle nommé validate_client_company. Je m'attends à ce qu'il n'en existe aucune, car l'action validate_client_company renvoie un partiel nommé message au lieu de rendre un modèle avec le nom par défaut pour cette action.

Dans l'action qui rend le script, vous devez configurer les variables d'instance puis dans le modèle pour cette action, vous devez utiliser les éléments suivants:

render :partial => 'live_validations/message' 

Il est certainement logique d'avoir un mini MVC empile dans la plus grande pile MVC, de sorte que vous pouvez exécuter des sous-actions dans l'exécution d'actions plus grandes. Pour ce scénario, vous souhaiterez peut-être regarder Cells. Cependant, vous ne pouvez pas le faire avec Rails lui-même.

0

Vous voulez probablement quelque chose comme ceci:

<script> 
$("#validate_company").live("keyup", function() { 
$("#company_info").load("<%= url_for :controller => 'live_validation', :action => 'validate_client_company' %>"); 
}); 
</script> 

Mais le reste de votre code est un peu de foiré ... rendu une partie de l'intérieur d'un contrôleur?

0

J'ai commencé à travailler!

<script> 
    $("#validate_company").live("keyup", function() { 
     $("#company_info").load("/live_validations/validate_client_company",{company:$('#validate_company').val()}); 
    }); 
</script> 
Questions connexes