Najnowsze zestawy zmian w Rubim 1.9.2 nie powodują już, że bieżący katalog jest .
częścią twojego LOAD_PATH
. Mam nietrywialną liczbę plików Rakefile, które zakładają, że .
jest to część LOAD_PATH
pliku, więc to je zepsuło (zgłosili „brak takiego pliku do załadowania” dla wszystkich instrukcji, które są oparte na ścieżce projektu). Czy było jakieś szczególne uzasadnienie, aby to zrobić?
Jeśli chodzi o poprawkę, dodawanie $: << "."
wszędzie działa, ale wydaje się niesamowicie hakerskie i nie chcę tego robić. Jaki jest preferowany sposób, aby moje pliki Rakefiles 1.9.2+ były kompatybilne?
require_relative
. Dzięki.require './filename'
działa tylko wtedy, gdy skrypt jest wykonywany z katalogiem roboczym ustawionym na ten sam katalog, w którym znajduje się skrypt. Często tak nie jest w projektach z wieloma katalogami.Są dwa powody:
Oba opierają się na tej samej podstawowej zasadzie: ogólnie rzecz biorąc, po prostu nie możesz wiedzieć, jaki jest bieżący katalog, kiedy twój kod jest uruchamiany. Oznacza to, że gdy potrzebujesz pliku i zależy od tego, czy znajduje się on w bieżącym katalogu, nie masz możliwości kontrolowania, czy ten plik w ogóle tam będzie, czy też jest to plik, którego faktycznie się tam spodziewasz.
źródło
.
, czyli bieżącego katalogu roboczego. Jeśli użytkownik znajdujecd
się w innym katalogu, bieżący katalog roboczy zmienia się, a teraz sąrequire
zupełnie inne pliki w zależności od tego, w jakim katalogu znajdował się użytkownik, gdy wywołał twój skrypt. Myślę, że to nie jest dobry pomysł.$: << File.dirname(__FILE__)
lib
katalog znajduje się na,$LOAD_PATH
a następnierequire
wszystkie pliki względemlib
. Innymi słowy: pozostawiam administratorowi ustalenie, jak$LOAD_PATH
poprawnie ustawić . Jeśli używasz RubyGems, jest to trywialne, ponieważ RubyGems automatycznie robi to za Ciebie, a jeśli używasz pakietów Debiana, to jest to zadanie opiekuna pakietu. W sumie wygląda na to, że całkiem nieźle się układa..
z$LOAD_PATH
, Ruby 1.9.2 wprowadza,require_relative
który… niespodzianka… jestrequire
plik w stosunku do lokalizacji aktualnie wykonywanego pliku (tj. WzględemFile.dirname(__FILE__)
).Jak wskazują inne odpowiedzi, jest to zagrożenie bezpieczeństwa, ponieważ
.
ścieżka ładowania odnosi się do obecnego katalogu roboczegoDir.pwd
, a nie do katalogu aktualnie ładowanego pliku. Więc ktokolwiek wykonuje twój skrypt, może to zmienić, przechodząc po prostucd
do innego katalogu. Niedobrze!Używam pełnych ścieżek zbudowanych z
__FILE__
jako alternatywy.W przeciwieństwie do
require_relative
tego jest wstecznie kompatybilny z Rubim 1.8.7.źródło
require Pathname.new(__FILE__).dirname + 'filename'
Posługiwać się
require_relative 'file_to_require'
Wrzuć to do swojego kodu, aby require_relative działał w 1.8.7:
źródło
'.' w twojej ścieżce od dawna uważano za złą rzecz w świecie Uniksa (patrz na przykład http://www.faqs.org/faqs/unix-faq/faq/part2/section-13.html ). Zakładam, że ludzie Ruby zostali przekonani, że mądrze jest tego nie robić.
źródło
Uznałem, że jest to kłopotliwa zmiana, dopóki nie zdałem sobie sprawy z kilku rzeczy.
Możesz ustawić RUBYLIB w swoim .profile (Unix) i żyć dalej tak, jak robiłeś to wcześniej:
export RUBYLIB="."
Ale jak wspomniano powyżej, od dawna uważano to za niebezpieczne.
W większości przypadków możesz uniknąć problemów, po prostu wywołując swoje skrypty Ruby z przedrostkiem „”. np ./scripts/server.
źródło
Jak zauważył Jörg W Mittag, myślę, że to, czego chcesz używać, to
require_relative
tak, aby żądany plik był powiązany z plikiem źródłowymrequire
deklaracji, a nie bieżącym katalogiem roboczym.Twoje zależności powinny być względne w stosunku do pliku kompilacji rake.
źródło