mirror of
				https://github.com/django/django.git
				synced 2025-10-31 09:41:08 +00:00 
			
		
		
		
	Fixed #28485 -- Made ExceptionReporter.get_traceback_frames() include frames without source code.
This commit is contained in:
		
				
					committed by
					
						
						Tim Graham
					
				
			
			
				
	
			
			
			
						parent
						
							90d7b912b9
						
					
				
				
					commit
					71d39571f4
				
			
							
								
								
									
										1
									
								
								AUTHORS
									
									
									
									
									
								
							
							
						
						
									
										1
									
								
								AUTHORS
									
									
									
									
									
								
							@@ -514,6 +514,7 @@ answer newbie questions, and generally made Django that much better:
 | 
			
		||||
    Martin Kosír <martin@martinkosir.net>
 | 
			
		||||
    Martin Mahner <http://www.mahner.org/>
 | 
			
		||||
    Martin Maney <http://www.chipy.org/Martin_Maney>
 | 
			
		||||
    Martin von Gagern <gagern@google.com>
 | 
			
		||||
    Mart Sõmermaa <http://mrts.pri.ee/>
 | 
			
		||||
    Marty Alchin <gulopine@gamemusic.org>
 | 
			
		||||
    masonsimon+django@gmail.com
 | 
			
		||||
 
 | 
			
		||||
@@ -418,22 +418,26 @@ class ExceptionReporter:
 | 
			
		||||
            pre_context_lineno, pre_context, context_line, post_context = self._get_lines_from_file(
 | 
			
		||||
                filename, lineno, 7, loader, module_name,
 | 
			
		||||
            )
 | 
			
		||||
            if pre_context_lineno is not None:
 | 
			
		||||
                frames.append({
 | 
			
		||||
                    'exc_cause': explicit_or_implicit_cause(exc_value),
 | 
			
		||||
                    'exc_cause_explicit': getattr(exc_value, '__cause__', True),
 | 
			
		||||
                    'tb': tb,
 | 
			
		||||
                    'type': 'django' if module_name.startswith('django.') else 'user',
 | 
			
		||||
                    'filename': filename,
 | 
			
		||||
                    'function': function,
 | 
			
		||||
                    'lineno': lineno + 1,
 | 
			
		||||
                    'vars': self.filter.get_traceback_frame_variables(self.request, tb.tb_frame),
 | 
			
		||||
                    'id': id(tb),
 | 
			
		||||
                    'pre_context': pre_context,
 | 
			
		||||
                    'context_line': context_line,
 | 
			
		||||
                    'post_context': post_context,
 | 
			
		||||
                    'pre_context_lineno': pre_context_lineno + 1,
 | 
			
		||||
                })
 | 
			
		||||
            if pre_context_lineno is None:
 | 
			
		||||
                pre_context_lineno = lineno
 | 
			
		||||
                pre_context = []
 | 
			
		||||
                context_line = '<source code not available>'
 | 
			
		||||
                post_context = []
 | 
			
		||||
            frames.append({
 | 
			
		||||
                'exc_cause': explicit_or_implicit_cause(exc_value),
 | 
			
		||||
                'exc_cause_explicit': getattr(exc_value, '__cause__', True),
 | 
			
		||||
                'tb': tb,
 | 
			
		||||
                'type': 'django' if module_name.startswith('django.') else 'user',
 | 
			
		||||
                'filename': filename,
 | 
			
		||||
                'function': function,
 | 
			
		||||
                'lineno': lineno + 1,
 | 
			
		||||
                'vars': self.filter.get_traceback_frame_variables(self.request, tb.tb_frame),
 | 
			
		||||
                'id': id(tb),
 | 
			
		||||
                'pre_context': pre_context,
 | 
			
		||||
                'context_line': context_line,
 | 
			
		||||
                'post_context': post_context,
 | 
			
		||||
                'pre_context_lineno': pre_context_lineno + 1,
 | 
			
		||||
            })
 | 
			
		||||
 | 
			
		||||
            # If the traceback for current exception is consumed, try the
 | 
			
		||||
            # other exception.
 | 
			
		||||
 
 | 
			
		||||
@@ -375,6 +375,27 @@ class ExceptionReporterTests(SimpleTestCase):
 | 
			
		||||
        self.assertIn(implicit_exc.format("Second exception"), text)
 | 
			
		||||
        self.assertEqual(3, text.count('<p>Final exception</p>'))
 | 
			
		||||
 | 
			
		||||
    def test_reporting_frames_without_source(self):
 | 
			
		||||
        try:
 | 
			
		||||
            source = "def funcName():\n    raise Error('Whoops')\nfuncName()"
 | 
			
		||||
            namespace = {}
 | 
			
		||||
            code = compile(source, 'generated', 'exec')
 | 
			
		||||
            exec(code, namespace)
 | 
			
		||||
        except Exception:
 | 
			
		||||
            exc_type, exc_value, tb = sys.exc_info()
 | 
			
		||||
        request = self.rf.get('/test_view/')
 | 
			
		||||
        reporter = ExceptionReporter(request, exc_type, exc_value, tb)
 | 
			
		||||
        frames = reporter.get_traceback_frames()
 | 
			
		||||
        last_frame = frames[-1]
 | 
			
		||||
        self.assertEqual(last_frame['context_line'], '<source code not available>')
 | 
			
		||||
        self.assertEqual(last_frame['filename'], 'generated')
 | 
			
		||||
        self.assertEqual(last_frame['function'], 'funcName')
 | 
			
		||||
        self.assertEqual(last_frame['lineno'], 2)
 | 
			
		||||
        html = reporter.get_traceback_html()
 | 
			
		||||
        self.assertIn('generated in funcName', html)
 | 
			
		||||
        text = reporter.get_traceback_text()
 | 
			
		||||
        self.assertIn('"generated" in funcName', text)
 | 
			
		||||
 | 
			
		||||
    def test_request_and_message(self):
 | 
			
		||||
        "A message can be provided in addition to a request"
 | 
			
		||||
        request = self.rf.get('/test_view/')
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user