diff --git a/src/core/annotation.js b/src/core/annotation.js index 6c3c81dec..20b7b7aa9 100644 --- a/src/core/annotation.js +++ b/src/core/annotation.js @@ -671,6 +671,12 @@ var WidgetAnnotation = (function WidgetAnnotationClosure() { var loopDict = dict; while (loopDict.has('Parent')) { loopDict = loopDict.get('Parent'); + if (!isDict(loopDict)) { + // Even though it is not allowed according to the PDF specification, + // bad PDF generators may provide a `Parent` entry that is not a + // dictionary, but `null` for example (issue 8143). + break; + } if (loopDict.has('T')) { fieldName.unshift(stringToPDFString(loopDict.get('T'))); diff --git a/test/unit/annotation_spec.js b/test/unit/annotation_spec.js index c2fb5728e..9693b4e58 100644 --- a/test/unit/annotation_spec.js +++ b/test/unit/annotation_spec.js @@ -805,6 +805,28 @@ describe('annotation', function() { expect(data.fieldName).toEqual('foo.bar.baz'); }); + + it('should construct the field name if a parent is not a dictionary ' + + '(issue 8143)', function() { + var parentDict = new Dict(); + parentDict.set('Parent', null); + parentDict.set('T', 'foo'); + + widgetDict.set('Parent', parentDict); + widgetDict.set('T', 'bar'); + + var widgetRef = new Ref(22, 0); + var xref = new XRefMock([ + { ref: widgetRef, data: widgetDict, } + ]); + + var annotation = annotationFactory.create(xref, widgetRef, + pdfManagerMock, idFactoryMock); + var data = annotation.data; + expect(data.annotationType).toEqual(AnnotationType.WIDGET); + + expect(data.fieldName).toEqual('foo.bar'); + }); }); describe('TextWidgetAnnotation', function() {