Sovrascrivere un metodo di mixin principale Rails ed essere ancora in grado di chiamare il vecchio metodo

StackOverflow https://stackoverflow.com/questions/1620468

  •  06-07-2019
  •  | 
  •  

Domanda

Ok, il titolo è confuso, ti dirò prima il mio problema:

il metodo polymorphic_url è stato modificato in Rails 2.2.1 per includere alcune funzionalità extra di cui ho bisogno. Tuttavia, voglio far funzionare ancora l'applicazione nelle versioni precedenti di Rails, quindi volevo correggere il comportamento 2.2.1 se è in esecuzione una versione precedente di Rails.

alias_method_chain in soccorso, giusto? Non riesco a farlo funzionare.

def polymorphic_url_with_compat(*args)
  whatever...
  return polymorphic_url(*args)
end
alias_method_chain :polymorphic_url, :compat

Ora ho provato per la prima volta a metterlo nell'helper - alias_method_chain fallisce perché polymorphic_url non è stato definito da allora. Quindi ho spostato lo stesso codice nel controller e non si verifica un errore, ma viene ignorato. Quindi ho provato ad applicarlo in ApplicationController :: Base con un plugin - polymorphic_url non è ancora definito.

polymorphic_url è definito nel modulo ActionController :: PolymorphicRoutes. Non so davvero quando / dove viene miscelato nel controller / nella vista.

Come posso avvolgere questo metodo nel modo in cui voglio?

È stato utile?

Soluzione

Prima di procedere, sei sicuro che polymorphic_url esistesse nella versione di Rails precedente alla 2.2.1?

Il tuo codice ha principalmente ragione, stai dimenticando di chiamare la versione originale del metodo. Che viene rinominato polymorphic_url_without_compat dopo la chiamata alias_method_chain.

class ActiveRecord::PolymorphicRoutes
  def polymorphic_url_with_compat(*args)
    whatever...
    return polymorphic_url_without_compat(*args)
  end
  alias_method_chain :polymorphic_url, :compat
end

Hai detto di aver provato ad aggiungerlo a un plugin, quindi potrebbe non essere necessario quanto segue se il bit precedente ha risolto il problema.

Il modo migliore per assicurarsi che sia caricato dopo il core delle rotaie è trasformarlo in un plugin.

$ script/generate plugin polymorphic_url_backport

Creerà uno stub di plugin. Tutte le indicazioni da questo punto in poi sono rilevanti per la directory del plugin creata.

In init.rb aggiungi

if RAILS_GEM_VERSION < "2.2.1"
  require File.dirname(__FILE__) + '/lib/yournamespace'
  ActionController::PolymorphicRoutes.send(:include, YourNameSpace::ActionController::PolymorphicRoutes) 
end

Quindi incolla il codice sopra in lib / yournamespace.rb

module YourNameSpace
  class ActiveRecord::PolymorphicRoutes
    def included(base)
      base.class_eval %~
        def polymorphic_url_with_compat(*args)
          whatever...
          return polymorphic_url_without_compat(*args)
        end
        alias_method_chain :polymorphic_url, :compat
      ~
    end
  end
end  

Assicurati solo che il plugin sia fornito con la tua applicazione e che non ci dovrebbero essere problemi. In alternativa potresti aggiungerlo alla libreria principale della tua rotaia di root, ma non sono sicuro di dove posizioneresti il ??codice richiesto per eseguirlo al momento giusto.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top