def method_missing(method_name, *args)
original_method_missing method_name, *args
end[/code]
Poczytałem trochę i wygląda mi na to, że tak samo w tym wypadku zadziała:
def method_missing(method_name, *args)
super
end
Bo wychodzi, mi że method missing w modelach AR wywołuje method_missing AR, więc super wystarczy.
Czy mogę użyć super zamiast aliasów i dlaczego?
Nie wiem dlaczego musisz użyć method_missing akurat w tym przypadku, nie da się bez magii ? Napisz może co konkretnie chcesz zrobić to znajdziemy lepsze rozwiązanie.
Używanie method_missing i aliasów prowadzi do dużych kłopotów ze zrozumieniem jak aplikacja działa jak już się rozrośnie i nie jest uważane za dobrą praktykę. To już drugi raz dzisiaj kiedy ktoś próbuje używać method_missing (w trywialnych przypadkach, tzn. przypuszczam że trywialnych, bo nie znam tutaj dokładnie problemu który chcesz rozwiązać) Ten przykład jest naprawdę “magiczny” bo oprócz method_missing robi jeszcze alias’a na method_missing co IMHO jest “overkillem” i może doporwadzić do tego, że ktoś kto przejmie po Tobie kod będzie usiłował Cię wytropić i zamordować
Motto na dzisiaj:
“Za każdym razem gdy używasz method_missing umiera gdzieś Lolcat”
[quote=tjeden]Poczytałem trochę i wygląda mi na to, że tak samo w tym wypadku zadziała:
def method_missing(method_name, *args)
super
end
[/quote]
Jeśli już masz korzystać z method_missing (chociaż podobnie jak hosiawak namawiam Cię żebyś tego nie robił) to zrób właśnie tak. A jeśli twierdzisz, że poczytałeś o tym to nie powinno Cię dziwić dlaczego to z ‘super’ działa :).
[quote=tjeden]Bo wychodzi, mi że method missing w modelach AR wywołuje method_missing AR, więc super wystarczy.
Czy mogę użyć super zamiast aliasów i dlaczego?[/quote]
Twoja klasa dziedziczy po ActiveRecord::Base, a wiec definiując w niej metodę “method_missing” przesłaniasz tą oryginalną, a więc ‘super’ w podklasie musi wywołać wersję z nadklasy.
No naprawdę, szkoda mi tych lolcatów, a przykład jest zbyt skomplikowany, by wrzucać go na forum. Swoją drogą ponieważ widzę, że skoro wygląda mi na to, że tylko method_missing się tu nadaje, a do tego jest to na tyle skomplikowane, że średnio mi się chce tłumaczyć co chcę zrobić, to przemyślę całość raz jeszcze. Może coś pokomplikowałem po drodze.
A swoją drogą, to skoro mamy w Rubym takie konstrukcje, to czemu z nich nie skorzystać od czasu do czasu? Taka magia naprawdę czasem potrafi zaoszczędzić dużo lini kodu. Przecież np. taki ActionMailer korzysta z method_missing? Ja wiem, że powinienem pisać kod, tak jakby osoba, która go przejmie była maniakiem i znała mój dokładny adres, ale czasami skorzystanie z szeroko rozumianego metaprogramowania aż się prosi.
Skoro przykład jest tak skomplikowany, że nie opiszesz na forum to jesteś usprawiedliwiony Niech żyje method_missing i umierają lolcaty! A tak na serio, to nie twierdzę, że kategorycznie nigdy nie można używać method_missing, tylko w dużej ilości przypadków da się prościej, bez magii. Nawet nie chodziło mi bardzo o method_missing co o aliasowanie tejże. Jeśli chodzi o budowanie jakiegoś DSL’a to lepiej zrobić method chaining albo rozpoznawać słownik w obrębie bloku. No ale skoro nie napiszesz o co dokładnie chodzi to nie mamy o czym dyskutować, szkoda
Ponieważ upewniłem się, że nie muszę korzystać z aliasów, to już je wywaliłem i teraz jest tylko method_missing z super (czyli nadal trochę szatan, ale mniejszy). O przykładzie chciałbym porozmawiać na następnym Wrugu. Jak będę miał trochę więcej czasu, to opiszę wcześniej przykład i podyskutujemy. Zaczynam się zastanawiać nad przyszłą krytyką, bo trochę mi moje rozwiązanie pachnie strzelaniem ze słonia do armaty.
UPDATE:
Z armaty do muchy miały być. Nie myślę dziś.
Jeżeli chodzi o method missing, albo inne techniki, które są specyficzne dla Rubiego, to też często się łapię na ich nadużywaniu. Każdy kto programuje w rubim powinien też pokodzić w jakimś języku, który reprezentuje bardziej tradycyjne podejście do programowania obiektowego (Java?).
A najlepszym tego przykładem są Railsy i Merb - Railsy pokazały wielu programistom jak można uprościć interfejs i umilić kodzenie, ale są też źródłem wielu złych praktyk… Teraz Merb (a właściwie Katz i spółka) muszą posprzątać ten bałagan
Nie wiem czy takim fanatycznym - sam pisał, że czasami trzeba użyć czegoś takiego, żeby zhackować czyjś kod, do którego nie ma się dostępu.
Pewnie też byś do tego inaczej podchodził jakbyś musiał refaktoryzować kod railsów, gdzie aż roi się od alias_method_chain (często w miejscach gdzie nie jest to zupełnie potrzebne…). Ostatnio na przykład szukałem implementacji błędów w dla form_for, strasznie się zdziwiłem jak już znalazłem to: http://github.com/rails/rails/blob/17e712d3a3d3934bb1f694d449d9a76a3ac715c1/actionpack/lib/action_view/helpers/active_record_helper.rb#L247 Po co w ogóle coś takiego? Rozumiem, że ktoś stwierdzi, że kod jest wtedy bardziej modularny i że można go rozbić na “concerns”, ale bez przesady… Jak ktoś się bawił na przykład helperami w merbie to na pewno potwierdzi, że tam to jest zabawa, a w railsach skakanie po plikach i szukanie gdzie jeszcze ktoś coś wcisnął z pomocą alias_method_chain…