问题
I'm trying to display comments in a template like this:
{{ url note.note }}
{{ url note.note_by }}
My problem is that my template is in another directory from where the view that "requests" the notes are. How do I link to a view in another directory (or more specifically; the note.note inside a function in a views.py in another directory)?
In the views.py in the SAME directory as the template, I am linking to the template like this:
def blah(request):
return render(request, 'site/blah.html')
And in the views.py where I request and save the comments (note.note) look like this:
def messages(request):
if request.method == "POST":
new_note_text = request.POST.get('new_note')
new_note = Note()
new_note.note = new_note_text
new_note.note_by = request.user
new_note.note_datetime = timezone.now()
new_note.save()
return render(request, 'theme/messages.html', context)
Edit:
urls.py in the SAME directory as the template:
from django.conf.urls import include, patterns, url
from site import views
urlpatterns = patterns('',
url(r'^test$', views.blah, name='blah'),
)
settings.py:
import os
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
SECRET_KEY = ''
# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True
ALLOWED_HOSTS = []
# Application definition
INSTALLED_APPS = (
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'app',
'theme',
'site',
)
MIDDLEWARE_CLASSES = (
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.auth.middleware.SessionAuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'django.middleware.security.SecurityMiddleware',
)
ROOT_URLCONF = 'app.urls'
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]
WSGI_APPLICATION = 'appen.wsgi.application'
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
}
}
LANGUAGE_CODE = 'en-us'
TIME_ZONE = 'Europe'
USE_I18N = True
USE_L10N = True
USE_TZ = True
STATIC_URL = '/static/'
回答1:
Django's reverse url resolver has one job. It takes the arguments fed to it(either through the {% url ... %}"
template tag or the urlresolves.reverse
in your python code.
As long as your code is in a valid Django configuration(Below) at start up time the directories templates and views are in isn't relevant. This particular example assumes you've included your apps in the settings.py
configuration and that your root urls.py
includes entries that delegate to the urls.py
files in the individual apps main
and notes
- templates
|
- main.html
- notes.html
- main
|
- views.py
- models.py
- urls.py
- notes
|
- views.py
- models.py
- urls.py
- urls.py
- settings.py
What do you need for this to work
so first lets look at main
I have to create a view function in views.py
from django.shortcuts import render
def main(request):
return render(request, 'main.html', {})
and a urls.py
entry in main/urls.py
from django.conf.urls import url
from . import views
urlpatterns = [
url(r'^$', main, name='main'),
]
So this is my main view. Lets assume I want to include a <ul>
with links to various notes from my other app. First things first I need to create a note/<note_id>
view. I am using the <note_id>
parameter to address my note entries.
in notes/views.py
I create a notes function that takes an note_id
keyword argument.
def notes(note_id=None):
#... Get note from database and put in context
return render(request, 'notes.html', {})
then create a notes/urls.py
entry for the view we've created.
from django.conf.urls import url, patterns
urlpatterns = patterns(
'main.views',
url(r'^(?P<note_id>[0-9]+)/?$','notes', name='notes'),
)
We then need to pull this all together using the root urls.py
file
from django.conf.urls import include, url
urlpatterns = [
url(r'^main/', include('main.urls')),
url(r'^notes/', include('notes.urls')),
]
So lets stop. What do we have right now? We have a view called main
that binds context
to the main.html
template and returns as a response some markup. We also have a urls.py
entry that tells the web server how to reach that view. We have the exact same thing for a view called notes
in a different app. Finally, we have a root urls.py
that pull my app-specific urls.py
files into the top-level.
What do we want to do? We want to include in main.html
a <ul>
filled with valid url references to our notes.
Since we already have everything setup this is easy we use the {% url ... %}
template tag with the appropriate information to resolve entries from our urls.py
files.
In our main.html
template we simply add something like this...
<ul>
<li> <a href="{% url "notes" note_id=1 %}">note 1</a></li>
<li> <a href="{% url "notes" note_id=2 %}">note 2</a></li>
<li> <a href="{% url "notes" note_id=3 %}">note 3</a></li>
</ul>
and when main.html
is invoked the markup above will look something like...
<ul>
<li> <a href="/notes/1">note 1</a></li>
<li> <a href="/notes/2">note 2</a></li>
<li> <a href="/notes/3">note 3</a></li>
</ul>
The important thing to remember here is what url
and urlresolver.reverse
actually do. They take a view name and some arguments and they convert them into a valid url as a string. Its a DRY approach to url management because later if you change notes
to notes_important
or something all of the templates will automatically fix everything for you.
来源:https://stackoverflow.com/questions/30557725/django-link-to-url-in-template-when-function-is-in-a-view-in-another-directory