mirror of
				https://github.com/django/django.git
				synced 2025-10-31 09:41:08 +00:00 
			
		
		
		
	Fixed #19299 -- Fixed Nullification of Foreign Keys To CharFields
Thanks tunixman for the report and Baptiste Mispelon and Shai Berger for reviews.
This commit is contained in:
		
							
								
								
									
										1
									
								
								AUTHORS
									
									
									
									
									
								
							
							
						
						
									
										1
									
								
								AUTHORS
									
									
									
									
									
								
							| @@ -646,6 +646,7 @@ answer newbie questions, and generally made Django that much better: | ||||
|     Rick Wagner <rwagner@physics.ucsd.edu> | ||||
|     Gavin Wahl <gavinwahl@gmail.com> | ||||
|     wam-djangobug@wamber.net | ||||
|     Albert Wang <aywang31@gmail.com> | ||||
|     Wang Chun <wangchun@exoweb.net> | ||||
|     Filip Wasilewski <filip.wasilewski@gmail.com> | ||||
|     Dan Watson <http://danwatson.net/> | ||||
|   | ||||
| @@ -1692,11 +1692,12 @@ class ForeignKey(ForeignObject): | ||||
|         return field_default | ||||
|  | ||||
|     def get_db_prep_save(self, value, connection): | ||||
|         if value == '' or value is None: | ||||
|         if value is None or (value == '' and | ||||
|                              (not self.related_field.empty_strings_allowed or | ||||
|                               connection.features.interprets_empty_strings_as_nulls)): | ||||
|             return None | ||||
|         else: | ||||
|             return self.related_field.get_db_prep_save(value, | ||||
|                 connection=connection) | ||||
|             return self.related_field.get_db_prep_save(value, connection=connection) | ||||
|  | ||||
|     def value_to_string(self, obj): | ||||
|         if not obj: | ||||
|   | ||||
| @@ -1416,9 +1416,12 @@ def get_cached_row(row, index_start, using, klass_info, offset=0, | ||||
|     klass, field_names, field_count, related_fields, reverse_related_fields, pk_idx = klass_info | ||||
|  | ||||
|     fields = row[index_start:index_start + field_count] | ||||
|     # If the pk column is None (or the Oracle equivalent ''), then the related | ||||
|     # If the pk column is None (or the equivalent '' in the case the | ||||
|     # connection interprets empty strings as nulls), then the related | ||||
|     # object must be non-existent - set the relation to None. | ||||
|     if fields[pk_idx] is None or fields[pk_idx] == '': | ||||
|     if (fields[pk_idx] is None or | ||||
|         (connections[using].features.interprets_empty_strings_as_nulls and | ||||
|          fields[pk_idx] == '')): | ||||
|         obj = None | ||||
|     elif field_names: | ||||
|         fields = list(fields) | ||||
|   | ||||
| @@ -72,12 +72,21 @@ class BooleanModel(models.Model): | ||||
|     string = models.CharField(max_length=10, default='abc') | ||||
|  | ||||
|  | ||||
| class PrimaryKeyCharModel(models.Model): | ||||
|     string = models.CharField(max_length=10, primary_key=True) | ||||
|  | ||||
|  | ||||
| class FksToBooleans(models.Model): | ||||
|     """Model wih FKs to models with {Null,}BooleanField's, #15040""" | ||||
|     bf = models.ForeignKey(BooleanModel) | ||||
|     nbf = models.ForeignKey(NullBooleanModel) | ||||
|  | ||||
|  | ||||
| class FkToChar(models.Model): | ||||
|     """Model with FK to a model with a CharField primary key, #19299""" | ||||
|     out = models.ForeignKey(PrimaryKeyCharModel) | ||||
|  | ||||
|  | ||||
| class RenamedField(models.Model): | ||||
|     modelname = models.IntegerField(name="fieldname", choices=((1, 'One'),)) | ||||
|  | ||||
|   | ||||
| @@ -22,8 +22,8 @@ from django.utils.functional import lazy | ||||
|  | ||||
| from .models import ( | ||||
|     Foo, Bar, Whiz, BigD, BigS, BigInt, Post, NullBooleanModel, | ||||
|     BooleanModel, DataModel, Document, RenamedField, | ||||
|     VerboseNameField, FksToBooleans) | ||||
|     BooleanModel, PrimaryKeyCharModel, DataModel, Document, RenamedField, | ||||
|     VerboseNameField, FksToBooleans, FkToChar) | ||||
|  | ||||
|  | ||||
| class BasicFieldTests(test.TestCase): | ||||
| @@ -146,6 +146,17 @@ class ForeignKeyTests(test.TestCase): | ||||
|         b = Bar.objects.create(b="bcd") | ||||
|         self.assertEqual(b.a, a) | ||||
|  | ||||
|     @test.skipIfDBFeature('interprets_empty_strings_as_nulls') | ||||
|     def test_empty_string_fk(self): | ||||
|         """ | ||||
|         Test that foreign key values to empty strings don't get converted | ||||
|         to None (#19299) | ||||
|         """ | ||||
|         char_model_empty = PrimaryKeyCharModel.objects.create(string='') | ||||
|         fk_model_empty = FkToChar.objects.create(out=char_model_empty) | ||||
|         fk_model_empty = FkToChar.objects.select_related('out').get(id=fk_model_empty.pk) | ||||
|         self.assertEqual(fk_model_empty.out, char_model_empty) | ||||
|  | ||||
|  | ||||
| class DateTimeFieldTests(unittest.TestCase): | ||||
|     def test_datetimefield_to_python_usecs(self): | ||||
|   | ||||
		Reference in New Issue
	
	Block a user