mirror of
				https://github.com/django/django.git
				synced 2025-10-31 09:41:08 +00:00 
			
		
		
		
	Added 'django-admin.py validate', which validates all installed models. Validation only handles common errors at this point, but we'll be improving it each time we think of a potential model syntax problem. Also changed the development Web server to validate automatically at server start.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@503 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
		| @@ -7,7 +7,9 @@ ACTION_MAPPING = { | ||||
|     'adminindex': management.get_admin_index, | ||||
|     'createsuperuser': management.createsuperuser, | ||||
| #     'dbcheck': management.database_check, | ||||
|     'init': management.init, | ||||
|     'inspectdb': management.inspectdb, | ||||
|     'install': management.install, | ||||
|     'runserver': management.runserver, | ||||
|     'sql': management.get_sql_create, | ||||
|     'sqlall': management.get_sql_all, | ||||
| @@ -18,8 +20,7 @@ ACTION_MAPPING = { | ||||
|     'sqlsequencereset': management.get_sql_sequence_reset, | ||||
|     'startapp': management.startapp, | ||||
|     'startproject': management.startproject, | ||||
|     'init': management.init, | ||||
|     'install': management.install, | ||||
|     'validate': management.validate, | ||||
| } | ||||
|  | ||||
| NO_SQL_TRANSACTION = ('adminindex', 'dbcheck', 'install', 'sqlindexes') | ||||
| @@ -65,7 +66,7 @@ def main(): | ||||
|         print_error("An action is required.", sys.argv[0]) | ||||
|     if not ACTION_MAPPING.has_key(action): | ||||
|         print_error("Your action, %r, was invalid." % action, sys.argv[0]) | ||||
|     if action in ('createsuperuser', 'init'): | ||||
|     if action in ('createsuperuser', 'init', 'validate'): | ||||
|         ACTION_MAPPING[action]() | ||||
|     elif action == 'inspectdb': | ||||
|         try: | ||||
|   | ||||
| @@ -483,6 +483,58 @@ def inspectdb(db_name): | ||||
| inspectdb.help_doc = "Introspects the database tables in the given database and outputs a Django model module." | ||||
| inspectdb.args = "[dbname]" | ||||
|  | ||||
| class ModelErrorCollection: | ||||
|     def __init__(self, outfile=sys.stdout): | ||||
|         self.errors = [] | ||||
|         self.outfile = outfile | ||||
|  | ||||
|     def add(self, opts, error): | ||||
|         self.errors.append((opts, error)) | ||||
|         self.outfile.write("%s.%s: %s\n" % (opts.module_name, opts.object_name, error)) | ||||
|  | ||||
| def validate(): | ||||
|     "Validates all installed models." | ||||
|     from django.core import meta | ||||
|     e = ModelErrorCollection() | ||||
|     module_list = meta.get_installed_model_modules() | ||||
|     for module in module_list: | ||||
|         for mod in module._MODELS: | ||||
|             opts = mod._meta | ||||
|  | ||||
|             # Do field-specific validation. | ||||
|             for f in opts.fields: | ||||
|                 if isinstance(f, meta.CharField) and f.maxlength in (None, 0): | ||||
|                     e.add(opts, '"%s" field: CharFields require a "maxlength" attribute.' % f.name) | ||||
|  | ||||
|             # Check admin attribute. | ||||
|             if opts.admin is not None and not isinstance(opts.admin, meta.Admin): | ||||
|                 e.add(opts, '"admin" attribute, if given, must be set to a meta.Admin() instance.') | ||||
|  | ||||
|             # Check ordering attribute. | ||||
|             if opts.ordering: | ||||
|                 for field_name in opts.ordering: | ||||
|                     if field_name == '?': continue | ||||
|                     if field_name.startswith('-'): | ||||
|                         field_name = field_name[1:] | ||||
|                     try: | ||||
|                         opts.get_field(field_name, many_to_many=False) | ||||
|                     except meta.FieldDoesNotExist: | ||||
|                         e.add(opts, '"ordering" refers to "%s", a field that doesn\'t exist.' % field_name) | ||||
|  | ||||
|             # Check core=True, if needed. | ||||
|             for rel_opts, rel_field in opts.get_inline_related_objects(): | ||||
|                 try: | ||||
|                     for f in rel_opts.fields: | ||||
|                         if f.core: | ||||
|                             raise StopIteration | ||||
|                     e.add(rel_opts, "At least one field in %s should have core=True, because it's being edited inline by %s.%s." % (rel_opts.object_name, opts.module_name, opts.object_name)) | ||||
|                 except StopIteration: | ||||
|                     pass | ||||
|  | ||||
|     num_errors = len(e.errors) | ||||
|     print '%s error%s found.' % (num_errors, num_errors != 1 and 's' or '') | ||||
| validate.args = '' | ||||
|  | ||||
| def runserver(port): | ||||
|     "Starts a lightweight Web server for development." | ||||
|     from django.core.servers.basehttp import run, AdminMediaHandler, WSGIServerException | ||||
| @@ -492,7 +544,9 @@ def runserver(port): | ||||
|         sys.exit(1) | ||||
|     def inner_run(): | ||||
|         from django.conf.settings import SETTINGS_MODULE | ||||
|         print "Starting server on port %s with settings module %r." % (port, SETTINGS_MODULE) | ||||
|         print "Validating models..." | ||||
|         validate() | ||||
|         print "\nStarting server on port %s with settings module %r." % (port, SETTINGS_MODULE) | ||||
|         print "Go to http://127.0.0.1:%s/ for Django." % port | ||||
|         print "Quit the server with CONTROL-C (Unix) or CTRL-BREAK (Windows)." | ||||
|         try: | ||||
|   | ||||
		Reference in New Issue
	
	Block a user