First checkin
This commit is contained in:
commit
d29100a692
Binary file not shown.
|
@ -0,0 +1,189 @@
|
||||||
|
# Setting the path
|
||||||
|
|
||||||
|
import os
|
||||||
|
gettext = lambda s: s
|
||||||
|
PROJECT_PATH = os.path.abspath(os.path.dirname(__file__))
|
||||||
|
|
||||||
|
|
||||||
|
# Django settings for blechreiz project.
|
||||||
|
|
||||||
|
DEBUG = True
|
||||||
|
TEMPLATE_DEBUG = DEBUG
|
||||||
|
|
||||||
|
ADMINS = (
|
||||||
|
# ('Your Name', 'your_email@example.com'),
|
||||||
|
)
|
||||||
|
|
||||||
|
MANAGERS = ADMINS
|
||||||
|
|
||||||
|
|
||||||
|
DATABASES = {
|
||||||
|
'default': {
|
||||||
|
'ENGINE': 'django.db.backends.sqlite3',
|
||||||
|
'NAME': os.path.join(PROJECT_PATH, 'database.sqlite'),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Hosts/domain names that are valid for this site; required if DEBUG is False
|
||||||
|
# See https://docs.djangoproject.com/en/1.5/ref/settings/#allowed-hosts
|
||||||
|
ALLOWED_HOSTS = []
|
||||||
|
|
||||||
|
# Local time zone for this installation. Choices can be found here:
|
||||||
|
# http://en.wikipedia.org/wiki/List_of_tz_zones_by_name
|
||||||
|
# although not all choices may be available on all operating systems.
|
||||||
|
# In a Windows environment this must be set to your system time zone.
|
||||||
|
TIME_ZONE = 'Europe/Berlin'
|
||||||
|
|
||||||
|
# Language code for this installation. All choices can be found here:
|
||||||
|
# http://www.i18nguy.com/unicode/language-identifiers.html
|
||||||
|
LANGUAGE_CODE = 'en-us'
|
||||||
|
|
||||||
|
SITE_ID = 1
|
||||||
|
|
||||||
|
# If you set this to False, Django will make some optimizations so as not
|
||||||
|
# to load the internationalization machinery.
|
||||||
|
USE_I18N = True
|
||||||
|
|
||||||
|
# If you set this to False, Django will not format dates, numbers and
|
||||||
|
# calendars according to the current locale.
|
||||||
|
USE_L10N = True
|
||||||
|
|
||||||
|
# If you set this to False, Django will not use timezone-aware datetimes.
|
||||||
|
USE_TZ = True
|
||||||
|
|
||||||
|
# Absolute filesystem path to the directory that will hold user-uploaded files.
|
||||||
|
# Example: "/var/www/example.com/media/"
|
||||||
|
#MEDIA_ROOT = PROJECT_PATH + "/media/"
|
||||||
|
MEDIA_ROOT = '/home/martin/workspace/blechreiz/media/'
|
||||||
|
|
||||||
|
# URL that handles the media served from MEDIA_ROOT. Make sure to use a
|
||||||
|
# trailing slash.
|
||||||
|
# Examples: "http://example.com/media/", "http://media.example.com/"
|
||||||
|
MEDIA_URL = 'media/'
|
||||||
|
|
||||||
|
# Absolute path to the directory static files should be collected to.
|
||||||
|
# Don't put anything in this directory yourself; store your static files
|
||||||
|
# in apps' "static/" subdirectories and in STATICFILES_DIRS.
|
||||||
|
# Example: "/var/www/example.com/static/"
|
||||||
|
STATIC_ROOT = ''
|
||||||
|
|
||||||
|
# URL prefix for static files.
|
||||||
|
# Example: "http://example.com/static/", "http://static.example.com/"
|
||||||
|
STATIC_URL = '/static/'
|
||||||
|
|
||||||
|
# Additional locations of static files
|
||||||
|
STATICFILES_DIRS = (
|
||||||
|
PROJECT_PATH + '/static',
|
||||||
|
# Put strings here, like "/home/html/static" or "C:/www/django/static".
|
||||||
|
# Always use forward slashes, even on Windows.
|
||||||
|
# Don't forget to use absolute paths, not relative paths.
|
||||||
|
)
|
||||||
|
|
||||||
|
# List of finder classes that know how to find static files in
|
||||||
|
# various locations.
|
||||||
|
STATICFILES_FINDERS = (
|
||||||
|
'django.contrib.staticfiles.finders.FileSystemFinder',
|
||||||
|
'django.contrib.staticfiles.finders.AppDirectoriesFinder',
|
||||||
|
# 'django.contrib.staticfiles.finders.DefaultStorageFinder',
|
||||||
|
)
|
||||||
|
|
||||||
|
# Make this unique, and don't share it with anybody.
|
||||||
|
SECRET_KEY = 'x$8&9s6t%eeg=wyhar87934wh_s$dbpm(73g4ho&n)9_wogj6p'
|
||||||
|
|
||||||
|
# List of callables that know how to import templates from various sources.
|
||||||
|
TEMPLATE_LOADERS = (
|
||||||
|
'django.template.loaders.filesystem.Loader',
|
||||||
|
'django.template.loaders.app_directories.Loader',
|
||||||
|
# 'django.template.loaders.eggs.Loader',
|
||||||
|
)
|
||||||
|
|
||||||
|
MIDDLEWARE_CLASSES = (
|
||||||
|
'django.middleware.common.CommonMiddleware',
|
||||||
|
'django.contrib.sessions.middleware.SessionMiddleware',
|
||||||
|
'django.middleware.csrf.CsrfViewMiddleware',
|
||||||
|
'django.contrib.auth.middleware.AuthenticationMiddleware',
|
||||||
|
'django.contrib.messages.middleware.MessageMiddleware',
|
||||||
|
# Uncomment the next line for simple clickjacking protection:
|
||||||
|
# 'django.middleware.clickjacking.XFrameOptionsMiddleware',
|
||||||
|
)
|
||||||
|
|
||||||
|
ROOT_URLCONF = 'blechreiz.urls'
|
||||||
|
|
||||||
|
# Python dotted path to the WSGI application used by Django's runserver.
|
||||||
|
WSGI_APPLICATION = 'blechreiz.wsgi.application'
|
||||||
|
|
||||||
|
TEMPLATE_DIRS = (
|
||||||
|
PROJECT_PATH + '/templates',
|
||||||
|
|
||||||
|
# Put strings here, like "/home/html/django_templates" or "C:/www/django/templates".
|
||||||
|
# Always use forward slashes, even on Windows.
|
||||||
|
# Don't forget to use absolute paths, not relative paths.
|
||||||
|
)
|
||||||
|
|
||||||
|
INSTALLED_APPS = (
|
||||||
|
'django.contrib.auth',
|
||||||
|
'django.contrib.contenttypes',
|
||||||
|
'django.contrib.sessions',
|
||||||
|
'django.contrib.sites',
|
||||||
|
'django.contrib.messages',
|
||||||
|
'django.contrib.staticfiles',
|
||||||
|
# Uncomment the next line to enable the admin:
|
||||||
|
'django.contrib.admin',
|
||||||
|
# Uncomment the next line to enable admin documentation:
|
||||||
|
'django.contrib.admindocs',
|
||||||
|
'crispy_forms',
|
||||||
|
'musicians'
|
||||||
|
)
|
||||||
|
|
||||||
|
CRISPY_TEMPLATE_PACK = 'bootstrap'
|
||||||
|
|
||||||
|
# A sample logging configuration. The only tangible logging
|
||||||
|
# performed by this configuration is to send an email to
|
||||||
|
# the site admins on every HTTP 500 error when DEBUG=False.
|
||||||
|
# See http://docs.djangoproject.com/en/dev/topics/logging for
|
||||||
|
# more details on how to customize your logging configuration.
|
||||||
|
LOGGING = {
|
||||||
|
'version': 1,
|
||||||
|
'disable_existing_loggers': True,
|
||||||
|
'formatters': {
|
||||||
|
'standard': {
|
||||||
|
'format' : "[%(asctime)s] %(levelname)s [%(name)s:%(lineno)s] %(message)s",
|
||||||
|
'datefmt' : "%d/%b/%Y %H:%M:%S"
|
||||||
|
},
|
||||||
|
},
|
||||||
|
'handlers': {
|
||||||
|
'null': {
|
||||||
|
'level':'DEBUG',
|
||||||
|
'class':'django.utils.log.NullHandler',
|
||||||
|
},
|
||||||
|
'logfile': {
|
||||||
|
'level':'DEBUG',
|
||||||
|
'class':'logging.handlers.RotatingFileHandler',
|
||||||
|
'filename': PROJECT_PATH + "/logfile",
|
||||||
|
'maxBytes': 50000,
|
||||||
|
'backupCount': 2,
|
||||||
|
'formatter': 'standard',
|
||||||
|
},
|
||||||
|
'console':{
|
||||||
|
'level':'INFO',
|
||||||
|
'class':'logging.StreamHandler',
|
||||||
|
'formatter': 'standard'
|
||||||
|
},
|
||||||
|
},
|
||||||
|
'loggers': {
|
||||||
|
'django': {
|
||||||
|
'handlers':['console'],
|
||||||
|
'propagate': True,
|
||||||
|
'level':'WARN',
|
||||||
|
},
|
||||||
|
'django.db.backends': {
|
||||||
|
'handlers': ['console'],
|
||||||
|
'level': 'DEBUG',
|
||||||
|
'propagate': False,
|
||||||
|
},
|
||||||
|
'musicians': {
|
||||||
|
'handlers': ['console', 'logfile'],
|
||||||
|
'level': 'DEBUG',
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,76 @@
|
||||||
|
/* Generated by http://www.cssportal.com */
|
||||||
|
|
||||||
|
/*@import url("reset.css");*/
|
||||||
|
|
||||||
|
body {
|
||||||
|
font-family: Verdana, Arial, Helvetica, sans-serif;
|
||||||
|
font-size: 13px;
|
||||||
|
color:#333
|
||||||
|
}
|
||||||
|
|
||||||
|
p {
|
||||||
|
padding: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#wrapper {
|
||||||
|
margin: 0 auto;
|
||||||
|
width: 1000px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#headerwrap {
|
||||||
|
width: 1000px;
|
||||||
|
float: left;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
#header {
|
||||||
|
height: 75px;
|
||||||
|
background: #FF6633;
|
||||||
|
border-radius: 10px;
|
||||||
|
border: 1px solid #eb521f;
|
||||||
|
margin: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#navigationwrap {
|
||||||
|
width: 1000px;
|
||||||
|
float: left;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
#navigation {
|
||||||
|
height: 40px;
|
||||||
|
background: #FFCC33;
|
||||||
|
border-radius: 10px;
|
||||||
|
border: 1px solid #ebb81f;
|
||||||
|
margin: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#contentwrap {
|
||||||
|
width: 850px;
|
||||||
|
float: left;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
#content {
|
||||||
|
background: #FFFFFF;
|
||||||
|
border-radius: 10px;
|
||||||
|
border: 1px solid #ebebeb;
|
||||||
|
margin: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#leftcolumnwrap {
|
||||||
|
width: 150px;
|
||||||
|
float: left;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
#leftcolumn {
|
||||||
|
background: #33CCFF;
|
||||||
|
border-radius: 10px;
|
||||||
|
border: 1px solid #1fb8eb;
|
||||||
|
margin: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,47 @@
|
||||||
|
/**
|
||||||
|
* Eric Meyer's Reset CSS v2.0 (http://meyerweb.com/eric/tools/css/reset/)
|
||||||
|
* http://www.cssportal.com
|
||||||
|
*/
|
||||||
|
html, body, div, span, applet, object, iframe,
|
||||||
|
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
|
||||||
|
a, abbr, acronym, address, big, cite, code,
|
||||||
|
del, dfn, em, img, ins, kbd, q, s, samp,
|
||||||
|
small, strike, strong, sub, sup, tt, var,
|
||||||
|
b, u, i, center,
|
||||||
|
dl, dt, dd, ol, ul, li,
|
||||||
|
fieldset, form, label, legend,
|
||||||
|
table, caption, tbody, tfoot, thead, tr, th, td,
|
||||||
|
article, aside, canvas, details, embed,
|
||||||
|
figure, figcaption, footer, header, hgroup,
|
||||||
|
menu, nav, output, ruby, section, summary,
|
||||||
|
time, mark, audio, video {
|
||||||
|
margin: 0;
|
||||||
|
padding: 0;
|
||||||
|
border: 0;
|
||||||
|
font-size: 100%;
|
||||||
|
font: inherit;
|
||||||
|
vertical-align: baseline;
|
||||||
|
}
|
||||||
|
/* HTML5 display-role reset for older browsers */
|
||||||
|
article, aside, details, figcaption, figure,
|
||||||
|
footer, header, hgroup, menu, nav, section {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
body {
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
ol, ul {
|
||||||
|
list-style: none;
|
||||||
|
}
|
||||||
|
blockquote, q {
|
||||||
|
quotes: none;
|
||||||
|
}
|
||||||
|
blockquote:before, blockquote:after,
|
||||||
|
q:before, q:after {
|
||||||
|
content: '';
|
||||||
|
content: none;
|
||||||
|
}
|
||||||
|
table {
|
||||||
|
border-collapse: collapse;
|
||||||
|
border-spacing: 0;
|
||||||
|
}
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,84 @@
|
||||||
|
{% load staticfiles %}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
<head>
|
||||||
|
<title>Main Page</title>
|
||||||
|
<!--[if IE]><script src="http://html5shiv.googlecode.com/svn/trunk/html5.js"></script><![endif]-->
|
||||||
|
<link rel="stylesheet" type="text/css" href="{% static "css/bootstrap.min.css" %}" media="screen">
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<title>{% block title %}Title{% endblock %}</title>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
<body>
|
||||||
|
|
||||||
|
<div class="navbar navbar-inverse navbar-fixed-top">
|
||||||
|
<div class="navbar-inner">
|
||||||
|
<div class="container-fluid">
|
||||||
|
{% block header %}
|
||||||
|
Header
|
||||||
|
{% endblock %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="container-fluid">
|
||||||
|
<div class="row-fluid">
|
||||||
|
<div class="span3">
|
||||||
|
<div class="well sidebar-nav">
|
||||||
|
{% block sidebar %}<p>Sidebar</p>{% endblock %}
|
||||||
|
</div><!--/.well -->
|
||||||
|
</div><!--/span-->
|
||||||
|
<div class="span9">
|
||||||
|
<div class="hero-unit">
|
||||||
|
{% block content %}
|
||||||
|
<h1>Hello, world!</h1>
|
||||||
|
<p>This is a template for a simple marketing or informational website. It includes a large callout called the hero unit and three supporting pieces of content. Use it as a starting point to create something more unique.</p>
|
||||||
|
<p><a href="#" class="btn btn-primary btn-large">Learn more »</a></p>
|
||||||
|
{% endblock %}
|
||||||
|
</div>
|
||||||
|
</div><!--/span-->
|
||||||
|
</div><!--/row-->
|
||||||
|
|
||||||
|
<hr>
|
||||||
|
|
||||||
|
<footer>
|
||||||
|
<p>© Martin Bauer</p>
|
||||||
|
</footer>
|
||||||
|
|
||||||
|
</div><!--/.fluid-container-->
|
||||||
|
|
||||||
|
<script src="http://code.jquery.com/jquery.js"></script>
|
||||||
|
<script src="{% static "js/bootstrap.min.js" %}"></script>
|
||||||
|
|
||||||
|
|
||||||
|
</body>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
</html>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,24 @@
|
||||||
|
from django.conf.urls import patterns, include, url
|
||||||
|
|
||||||
|
from django.contrib import admin
|
||||||
|
|
||||||
|
from musicians.views import MusicianList, MusicianUpdate
|
||||||
|
from musicians.views import user_edit
|
||||||
|
|
||||||
|
|
||||||
|
admin.autodiscover()
|
||||||
|
|
||||||
|
urlpatterns = patterns('',
|
||||||
|
# Examples:
|
||||||
|
# url(r'^$', 'blechreiz.views.home', name='home'),
|
||||||
|
# url(r'^blechreiz/', include('blechreiz.foo.urls')),
|
||||||
|
|
||||||
|
# Uncomment the admin/doc line below to enable admin documentation:
|
||||||
|
url(r'^admin/doc/', include('django.contrib.admindocs.urls')),
|
||||||
|
|
||||||
|
# Uncomment the next line to enable the admin:
|
||||||
|
url(r'^admin/', include(admin.site.urls)),
|
||||||
|
|
||||||
|
url(r'^musicians/$', MusicianList.as_view() ),
|
||||||
|
url(r'^musicians/(?P<username>[\w]+)$', user_edit ),
|
||||||
|
)
|
|
@ -0,0 +1,32 @@
|
||||||
|
"""
|
||||||
|
WSGI config for blechreiz project.
|
||||||
|
|
||||||
|
This module contains the WSGI application used by Django's development server
|
||||||
|
and any production WSGI deployments. It should expose a module-level variable
|
||||||
|
named ``application``. Django's ``runserver`` and ``runfcgi`` commands discover
|
||||||
|
this application via the ``WSGI_APPLICATION`` setting.
|
||||||
|
|
||||||
|
Usually you will have the standard Django WSGI application here, but it also
|
||||||
|
might make sense to replace the whole Django WSGI application with a custom one
|
||||||
|
that later delegates to the Django one. For example, you could introduce WSGI
|
||||||
|
middleware here, or combine a Django application with an application of another
|
||||||
|
framework.
|
||||||
|
|
||||||
|
"""
|
||||||
|
import os
|
||||||
|
|
||||||
|
# We defer to a DJANGO_SETTINGS_MODULE already in the environment. This breaks
|
||||||
|
# if running multiple sites in the same mod_wsgi process. To fix this, use
|
||||||
|
# mod_wsgi daemon mode with each site in its own daemon process, or use
|
||||||
|
# os.environ["DJANGO_SETTINGS_MODULE"] = "blechreiz.settings"
|
||||||
|
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "blechreiz.settings")
|
||||||
|
|
||||||
|
# This application object is used by any WSGI server configured to use this
|
||||||
|
# file. This includes Django's development server, if the WSGI_APPLICATION
|
||||||
|
# setting points here.
|
||||||
|
from django.core.wsgi import get_wsgi_application
|
||||||
|
application = get_wsgi_application()
|
||||||
|
|
||||||
|
# Apply WSGI middleware here.
|
||||||
|
# from helloworld.wsgi import HelloWorldApplication
|
||||||
|
# application = HelloWorldApplication(application)
|
|
@ -0,0 +1,10 @@
|
||||||
|
#!/usr/bin/env python
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "blechreiz.settings")
|
||||||
|
|
||||||
|
from django.core.management import execute_from_command_line
|
||||||
|
|
||||||
|
execute_from_command_line(sys.argv)
|
|
@ -0,0 +1,29 @@
|
||||||
|
from django.contrib import admin
|
||||||
|
from django.contrib.auth.admin import UserAdmin
|
||||||
|
from django.contrib.auth.models import User
|
||||||
|
from django.utils.translation import ugettext as _
|
||||||
|
|
||||||
|
|
||||||
|
from musicians.models import Musician, PhoneNumber
|
||||||
|
|
||||||
|
|
||||||
|
class PhoneNumberInline( admin.TabularInline ):
|
||||||
|
model = PhoneNumber
|
||||||
|
extra = 3
|
||||||
|
|
||||||
|
# Define an inline admin descriptor for Musician model
|
||||||
|
# which acts a bit like a singleton
|
||||||
|
class MusicianInline( admin.StackedInline ):
|
||||||
|
model = Musician
|
||||||
|
can_delete = False
|
||||||
|
verbose_name_plural = _('musicians')
|
||||||
|
verbose_name = _('musician')
|
||||||
|
|
||||||
|
# Define a new User admin
|
||||||
|
class UserAdmin( UserAdmin ):
|
||||||
|
inlines = (MusicianInline, PhoneNumberInline )
|
||||||
|
|
||||||
|
# Re-register UserAdmin
|
||||||
|
admin.site.unregister( User )
|
||||||
|
admin.site.register(User, UserAdmin)
|
||||||
|
|
|
@ -0,0 +1,44 @@
|
||||||
|
from django.db import models
|
||||||
|
from django.contrib.auth.models import User
|
||||||
|
from django.utils.translation import ugettext as _
|
||||||
|
|
||||||
|
import os
|
||||||
|
|
||||||
|
INSTRUMENTS = (
|
||||||
|
('TR', _('Trumpet') ),
|
||||||
|
('TRB', _('Trombone') ),
|
||||||
|
('EUPH',_('Euphonium') ),
|
||||||
|
('TUBA',_('Tuba') )
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class PhoneNumber( models.Model ):
|
||||||
|
user = models.OneToOneField( User )
|
||||||
|
|
||||||
|
desc = models.CharField( max_length=15 )
|
||||||
|
number = models.CharField( max_length=25 )
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def musicianPictureName( musician, originalName ):
|
||||||
|
fileExtension = os.path.splitext(originalName)[1]
|
||||||
|
return "user_images/" + musician.user.username + fileExtension
|
||||||
|
|
||||||
|
|
||||||
|
class Musician( models.Model ):
|
||||||
|
# Link to user object, contains first name and last name
|
||||||
|
user = models.OneToOneField( User )
|
||||||
|
|
||||||
|
# Properties
|
||||||
|
image = models.ImageField( upload_to = musicianPictureName )
|
||||||
|
|
||||||
|
instrument = models.CharField( max_length=4, choices=INSTRUMENTS, blank=True )
|
||||||
|
birthday = models.DateField( null=True )
|
||||||
|
street = models.CharField( max_length=80, blank=True )
|
||||||
|
city = models.CharField( max_length=40, blank=True )
|
||||||
|
zip_code = models.IntegerField( null=True)
|
||||||
|
|
||||||
|
public_description = models.TextField( blank=True )
|
||||||
|
|
|
@ -0,0 +1,15 @@
|
||||||
|
{% extends "base.html" %}
|
||||||
|
|
||||||
|
{% load crispy_forms_tags %}
|
||||||
|
|
||||||
|
{% block content %}
|
||||||
|
|
||||||
|
{% crispy form %}
|
||||||
|
|
||||||
|
<!--
|
||||||
|
<form action="/musicians/martin" method="post">
|
||||||
|
{% csrf_token %}
|
||||||
|
{{ form.as_p|crispy }}
|
||||||
|
<input type="submit" value="Submit" />
|
||||||
|
</form> -->
|
||||||
|
{% endblock %}
|
|
@ -0,0 +1,10 @@
|
||||||
|
{% extends "base.html" %}
|
||||||
|
|
||||||
|
{% block content %}
|
||||||
|
<h2>Musicians</h2>
|
||||||
|
<ul>
|
||||||
|
{% for musician in object_list %}
|
||||||
|
<li>{{ musician.user.username }}</li>
|
||||||
|
{% endfor %}
|
||||||
|
</ul>
|
||||||
|
{% endblock %}
|
|
@ -0,0 +1,16 @@
|
||||||
|
"""
|
||||||
|
This file demonstrates writing tests using the unittest module. These will pass
|
||||||
|
when you run "manage.py test".
|
||||||
|
|
||||||
|
Replace this with more appropriate tests for your application.
|
||||||
|
"""
|
||||||
|
|
||||||
|
from django.test import TestCase
|
||||||
|
|
||||||
|
|
||||||
|
class SimpleTest(TestCase):
|
||||||
|
def test_basic_addition(self):
|
||||||
|
"""
|
||||||
|
Tests that 1 + 1 always equals 2.
|
||||||
|
"""
|
||||||
|
self.assertEqual(1 + 1, 2)
|
|
@ -0,0 +1,104 @@
|
||||||
|
|
||||||
|
from django.views.generic.edit import UpdateView
|
||||||
|
from django.views.generic import ListView
|
||||||
|
from musicians.models import Musician
|
||||||
|
from django import forms
|
||||||
|
from django.http import HttpResponseRedirect
|
||||||
|
from django.http import HttpResponse
|
||||||
|
from django.shortcuts import render
|
||||||
|
from django.shortcuts import get_object_or_404
|
||||||
|
|
||||||
|
from crispy_forms.helper import FormHelper
|
||||||
|
from crispy_forms.layout import Submit
|
||||||
|
from crispy_forms.layout import Layout, Fieldset, ButtonHolder, Submit
|
||||||
|
|
||||||
|
|
||||||
|
class MusicianList( ListView):
|
||||||
|
model = Musician
|
||||||
|
|
||||||
|
|
||||||
|
class UserEditForm(forms.ModelForm):
|
||||||
|
|
||||||
|
first_name = forms.CharField( max_length = 60)
|
||||||
|
last_name = forms.CharField( max_length = 60)
|
||||||
|
email = forms.EmailField()
|
||||||
|
|
||||||
|
def __init__(self, *args, **kw):
|
||||||
|
|
||||||
|
if 'instance' in kw.keys():
|
||||||
|
user = kw['instance'].user
|
||||||
|
initVals = { 'first_name': user.first_name,
|
||||||
|
'last_name': user.last_name,
|
||||||
|
'email': user.email }
|
||||||
|
if not 'initial' in kw.keys():
|
||||||
|
kw['initial'] = initVals
|
||||||
|
else:
|
||||||
|
kw['initial'].update(initVals)
|
||||||
|
|
||||||
|
super(UserEditForm, self).__init__(*args, **kw)
|
||||||
|
|
||||||
|
self.helper = FormHelper()
|
||||||
|
self.helper.form_id = 'id-exampleForm'
|
||||||
|
self.helper.form_class = 'blueForms'
|
||||||
|
self.helper.form_method = 'post'
|
||||||
|
self.helper.form_action = '/musicians/martin' # TODO
|
||||||
|
|
||||||
|
self.helper.add_input(Submit('submit', 'Submit'))
|
||||||
|
|
||||||
|
self.helper.form_class = 'form-horizontal'
|
||||||
|
#self.helper.layout = Layout(
|
||||||
|
# Fieldset(
|
||||||
|
# 'Edit User',
|
||||||
|
# 'first_name',
|
||||||
|
# 'last_name',
|
||||||
|
# 'birthday',
|
||||||
|
# ),
|
||||||
|
#)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
self.fields.keyOrder.remove('first_name')
|
||||||
|
self.fields.keyOrder.remove('last_name')
|
||||||
|
self.fields.keyOrder.remove('email')
|
||||||
|
|
||||||
|
self.fields.keyOrder.insert(0, 'first_name')
|
||||||
|
self.fields.keyOrder.insert(1, 'last_name')
|
||||||
|
self.fields.keyOrder.insert(2, 'email')
|
||||||
|
|
||||||
|
def save(self):
|
||||||
|
if self.is_valid():
|
||||||
|
super(UserEditForm,self).save()
|
||||||
|
self.instance.user.first_name = self.cleaned_data['first_name']
|
||||||
|
self.instance.user.last_name = self.cleaned_data['last_name']
|
||||||
|
self.instance.user.email = self.cleaned_data['email']
|
||||||
|
self.instance.user.save()
|
||||||
|
|
||||||
|
class Meta:
|
||||||
|
model = Musician
|
||||||
|
exclude = [ 'user','image' ]
|
||||||
|
#fields = '__all__'
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def user_edit( request, username ):
|
||||||
|
|
||||||
|
musician = get_object_or_404(Musician, user__username=username )
|
||||||
|
|
||||||
|
if request.method == 'POST': # If the form has been submitted...
|
||||||
|
form = UserEditForm(request.POST) # A form bound to the POST data
|
||||||
|
form.instance = musician
|
||||||
|
if form.is_valid(): # All validation rules pass
|
||||||
|
form.save()
|
||||||
|
return HttpResponseRedirect('/musicians/' + username) # Redirect after POST
|
||||||
|
else:
|
||||||
|
form = UserEditForm( instance= musician )
|
||||||
|
|
||||||
|
return render(request, 'musicians/musician_edit.html', { 'form': form, } )
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class MusicianUpdate( UpdateView ):
|
||||||
|
model = Musician
|
||||||
|
#fields = []
|
||||||
|
template_name = "musicians/musician_edit.html"
|
||||||
|
success_url = '/books/'
|
Loading…
Reference in New Issue