2012-04-25 11 views
5

Mam pytanie dotyczące umieszczania aplikacji Django w podkatalogu "apps". Mam aplikację o nazwie "faktura" w katalogu projektu_root. Nie podoba mi się to, że leży tam i chcę przechowywać wszystkie moje aplikacje w podkatalogu "apps".Przenoszenie aplikacji Django do podfolderu i url.py error

Więc dowiedziałem się, że mogę rozszerzyć ścieżkę Pythona do podkatalogu "apps", więc po przejrzeniu w Internecie dodałem ten ciąg do settings.py: sys.path.insert (0, os.path.join (PROJECT_PATH, "apps")). Następnie dodałem aplikację do INSTALLED_APPS jak "faktura". Wszystko działało sprawnie, dopóki nie dodałem adresu url (r '^ faktura /', include ('faktura.urls')) do urls.py w katalogu głównym. Od tego czasu Django wyświetla komunikat o błędzie "Brak modułu o nazwie faktura". Pełne wstrzymanie dotyczy: http://dpaste.com/737380/

Co może być nie tak, dlaczego tylko urls.py nie może znaleźć aplikacji? I nie może znaleźć tej aplikacji, jeśli dodałem ją do PATH? Spędziłem ranek próbując dowiedzieć się, co jest nie tak i teraz potrzebuję twojej pomocy.

Odpowiedz

1

Aby zachować swoje aplikacje Django w podfolderze (takich jak aplikacje /), najpierw należy dodać następujące wpisy do settings.py:

import os

PROJECT_ROOT = os.path.dirname(__file__)

potem w manage.py:

!

Tuż pod #/usr/bin/env python add:

import sys

from os.path import abspath, dirname, join

from site import addsitedir

Tuż przed jeśli __name__ == "__main__": dodaj:

sys.path.insert(0, join(settings.PROJECT_ROOT, "apps"))

+1

Yep tym działa ... ale jeśli użyjesz - tak jak ja - uwsgi jako serwera aplikacji, to powinieneś również zastosować wstawkę do pliku wsgi.py. – Paul

+1

Czy naprawdę potrzebujesz nieużywanego importu (addeditedir, dirname, abspath)? Czy są one pozostawione z poprzedniej wersji tej odpowiedzi? –

+1

Modyfikowanie sys.path to zły pomysł. https://youtu.be/bAcfPzxB3dk?t=233 –

9

Nie wiem dlaczego poprzedni odpowiedź dostaje -1 oprócz może kilka zbędnych linii, które można poprawić. W każdym razie znalazłem nieco inną metodę, która nie wymaga dodawania niczego do ścieżki Pythona.

To moja ostateczna struktura katalogów, wyjaśnię za chwilę:

mysite 
├── mysite 
│ ├── __init__.py 
│ ├── settings.py 
│ ├── urls.py 
│ └── wsgi.py 
├── apps 
│ ├── __init__.py 
│ └── myfirstapp 
│  ├── __init__.py 
│  ├── admin.py 
│  ├── models.py 
│  ├── tests.py 
│  └── views.py 
└── manage.py 

Nieważne, czy masz tylko stworzył swój projekt lub jeśli chcesz przenieść swoje aplikacje, należy utworzyć podkatalog apps który powinien zawierać Twoje aplikacje. Sztuką jest dodanie do tego katalogu __init__.py.

mkdir apps 
touch apps/__init__.py 

Teraz możesz przenieść istniejące aplikacje do podkatalogu apps. Jeśli chcesz utworzyć nową zamiast oto komendy:

python manage.py mysecondapp 
mv mysecondapp apps/ 

UWAGA: Nie ulec pokusie, aby zadzwonić python manage.py ./apps/mysecondapp. Z jakiegoś powodu powoduje to usunięcie wszystkich innych aplikacji z tego katalogu. Właśnie straciłem dzień pracy.

Następnie należy poprawić kilka importów.Twój settings.py powinna być poprzedzona apps:

INSTALLED_APPS = (
    ... 
    'apps.myfirstapp', 
    'apps.mysecondapp' 
) 

Wreszcie naprawić projektu urls.py poprzedzający apps:

urlpatterns = patterns('', 
    url(r'^myfirstapp', include('apps.myfirstapp.urls')), 
    ... 
) 

W zależności od tego, jak je napisał, to polubisz też trzeba rozwiązać kilka importu wewnątrz aplikacja. Albo po prostu użyj from models import MyFirstModel lub przedrostek go używając from apps.myfirstapp.models import MyFirstModel.

W skrócie, jeśli stworzysz katalog apps jako pakiet python (dodając __init__.py), możesz go użyć jako części ścieżki importu. Powinno to działać niezależnie od metody wdrażania bez dodatkowej konfiguracji.

+0

Wpadłem na problem, który nie został rozwiązany w tej odpowiedzi, ponieważ urls.py w apps/myfirstapp musiał mieć pierwszy argument wzorców (...) ustawione na "apps.myfirstapp", tak jak poprzednio to zrobiłem, to czyta tylko "myfirstapp". Wyniki debugowania Django były znacznie mniej przydatne niż to. – Ethereal

+1

from apps.myfirstapp.models import MyFirstModel nie działa w pliku secondapps model.Nie wiem dlaczego .. – tyan

0

@Radu Gheorghiu's odpowiedź; Edytowanie pliku settings.py nie jest konieczne, a wiersz ścieżki wstawiania można skondensować do 1 linii kodu.

sys.path.insert(0, os.path.join(os.path.dirname(__file__), "apps")) 

I pozyskiwane tę odpowiedź od http://obroll.com/nested-application-inside-apps-sub-folder-in-django-1-3/

+0

Proszę nie tworzyć odpowiedzi na odpowiedź. Jeśli chcesz dodać coś do odpowiedzi Radu, użyj funkcji komentarza. – Silicomancer

1

Korzystanie BASE_DIR zmienna od settings.py. Powinno być już zdefiniowane:

BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 

Lepiej nie używać atrybutu __file__ w manage.py i wsgi.py, ponieważ znajdują się one w różnych katalogach.

Tak, tylko dodać następujące manage.py i wsgi.py (i do celery.py jeśli używasz Seler):

from django.conf import settings 
    sys.path.append(os.path.join(settings.BASE_DIR, "apps")) 

Będziesz skończyć z następującą strukturą projektu:

project 
├── project 
│ ├── __init__.py 
│ ├── celery.py 
│ ├── settings.py 
│ ├── urls.py 
│ └── wsgi.py 
├── apps 
│ ├── app1 
│ └── app2 
└── manage.py 
Powiązane problemy