1. 08 Sep, 2021 12 commits
    • Eduardo Sanz García's avatar
      Add three unit tests to check `_removeFrame` callback · be1c6910
      Eduardo Sanz García authored
      `_removeFrame` must be called in these three scenarios:
      
      - `enable-annotation` attribute is removed from iframe
      - `src` attribute is modified in the iframe
      - iframe is deleted
      
      When the iframe is deleted there are two possible paths for the execution of
      the `_removeFrame`:
      
      1. First and faster execution of `_removeFrame`: `iframe.remove()`
         triggers the `unload` event which calls the `_removeFrame`
      
      2. Second and delayed execution of `_removeFrame`: `iframe.remove()`
         triggers the `MutationObserver` (debounced by 40 ms). This could
         cause the `_removeFrame` to be fired if the first path would not
         remove the iframe from the list of `_handledFrames`.
      
      I moved the addition and deletion of the iframes to `_handledFrames` as
      earlier as possible in the `_addFrame` and `_removeFrame` methods to
      avoid racing conditions. A consequence of this is that the `_addFrame`
      is executed only once per iframe. If it fails (for example, because the
      iframe is from a different origin) it is not constantly retried.
      be1c6910
    • Eduardo Sanz García's avatar
      Add unit testing for the `FrameObserver` class · d0e56e8a
      Eduardo Sanz García authored
      The `FrameObserver` unit test now exercise the whole class, not just the
      `findFrames` function.
      
      On a future commit, we will inline the `findFrames functionality.
      d0e56e8a
    • Eduardo Sanz García's avatar
      Transform `onDocumentReady` on Promise-based function · fde04c8b
      Eduardo Sanz García authored
      `onDocumentReady` returns now a Promise instead of calling a callback.
      fde04c8b
    • Eduardo Sanz García's avatar
      Rename `isDocumentReady` to `onDocumentReady` · 895077ca
      Eduardo Sanz García authored
      The name of `isDocumentReady` gives the impressiong that the function
      would return a boolean.  `onDocumentReady`, on the other hand, expresses
      more clearly that the execution of the callback will be triggered after
      the iframe's documen is ready (loaded and parsed).
      
      On a follow up commit I change the `onDocumentReady` to return a Promise
      instead of executing a callback.
      895077ca
    • Eduardo Sanz García's avatar
      Use `Set` data structure instead of `Array` · 91c4b724
      Eduardo Sanz García authored
      `Set` is a better data structure because it has a faster search: `Set.has` has a O(1) while `Array.includes` has a O(n).
      91c4b724
    • Eduardo Sanz García's avatar
      Move `frame-util` functions to other files · fb7acdbf
      Eduardo Sanz García authored
      Moved `frame-util` functionality to `frame-observer.js` and
      `hypothesis-injector.js`:
      
      - `isAccessible`, `findFrames` and `isDocumentReady` functions to
        `frame-observer.js`, and
      
      - `hasHypothesis` and `injectHypothesis` functions to
        `hypothesis-injector.js`
      
      Renamed and move `src/annotator/util/test/frame-util-test.js` to
      `src/annotator/test/frame-observer-test.js`. This unit test only
      exercise the `findFrames` function.
      fb7acdbf
    • Eduardo Sanz García's avatar
      Run prettier on shadow-dom.mustache · f4db84d9
      Eduardo Sanz García authored
      I run this command `prettier -w --parser html` on `shadow-dom.mustache`
      f4db84d9
    • Eduardo Sanz García's avatar
      Fix type issue with the latest frontend-shared version · 60386124
      Eduardo Sanz García authored
      In the latest version of the frontent-shared package, `extraRoute` has a
      mandatory property `group` that must be either
      `"home" | "foundations" | "patterns" | "components"`;
      
      There are three ways to fix this:
      
      * make the `group` property optional in the frontend-shared package (I
        don't know if that's a good idea).
      
      * cast the `string` type to the one of the allowed types: `    group:
        /** @type {'components'} */ ('components'),`
      
      * cast the `extraRoute` (this PR).
      60386124
    • Eduardo Sanz García's avatar
      Improvements based on PR feedback · da2a14f4
      Eduardo Sanz García authored
      da2a14f4
    • Eduardo Sanz García's avatar
      Move the Hypothesis script inside the body · 9680793e
      Eduardo Sanz García authored
      Edge 17 complains if the script is outside the body.
      9680793e
    • Eduardo Sanz García's avatar
      Add cross-origin annotatable iframe dev server scenario · 3ff2f1b7
      Eduardo Sanz García authored
      The current inter-frame communication doesn't work if an annotatable
      (guest) iframe is from a different origin than the host frame (see
      https://github.com/hypothesis/client/pull/3611#issue-696947005). This
      will be fixed in a more comprehensive overhaul of the inter-face
      communication (see https://github.com/hypothesis/client/issues/3533).
      
      Meanwhile, I add a scenario into the local dev server where the
      annotatable iframe is from an origin different than the host frame. For
      this, I needed to spawn an additional dev server at port 3002):
      
      ```
      [11:32:50] Dev web server started at http://localhost:3000/
      [11:32:50] Dev web server started at http://localhost:3002/
      ```
      
      Close #3629
      3ff2f1b7
    • Robert Knight's avatar
      Fix security error mixing cross-origin frames and promises in old browsers · e04e8b70
      Robert Knight authored
      Fix an issue where the sidebar failed to appear in Safari 11 and Chrome
      63 when returning a cross-origin Window from a Promise `then` callback.
      In these browsers an exception is triggered when the browser tries to
      test if the return value is a Promise that can be unwrapped.
      
      The issue was resolved in more recent browsers by adding an undefined
      `then` property to cross origin objects. [1]
      
      [1] https://github.com/whatwg/dom/issues/536
      e04e8b70
  2. 06 Sep, 2021 12 commits
  3. 03 Sep, 2021 1 commit
    • Eduardo Sanz García's avatar
      Move `listener-collection.js` to `src/shared` · c91cbf0e
      Eduardo Sanz García authored
      `src/shared/port-rpc.js` depended on
      `src/annotation/util/listener-collection.js`. Files in the `src/shared`
      folder should not have dependencies on `src/annotation`.
      
      `ListenerCollection` is a very general utility and the placement in
      `src/shared` seems correct.
      
      I took the opportunity to reorder the imports according to our
      conventions.
      c91cbf0e
  4. 02 Sep, 2021 1 commit
  5. 01 Sep, 2021 1 commit
    • Robert Knight's avatar
      Fail anchoring in PDFs if there is no quote selector · 47706128
      Robert Knight authored
      Changes in text rendering across PDF.js versions can render position
      selectors invalid. Therefore any anchoring done with position selectors must
      be checked against the quote, as we do with HTML annotations.
      
      This commit disallows anchoring using only position selectors in PDFs
      and restructures `anchor` control flow using async/await to make it
      easier to follow.
      
      We have been capturing quote selectors with PDF annotations forever, so
      there should be no impact on old annotations.
      47706128
  6. 31 Aug, 2021 7 commits
    • dependabot[bot]'s avatar
      Bump npm-packlist from 2.2.2 to 3.0.0 · 1651c1cc
      dependabot[bot] authored
      Bumps [npm-packlist](https://github.com/npm/npm-packlist) from 2.2.2 to 3.0.0.
      - [Release notes](https://github.com/npm/npm-packlist/releases)
      - [Commits](https://github.com/npm/npm-packlist/compare/v2.2.2...v3.0.0)
      
      ---
      updated-dependencies:
      - dependency-name: npm-packlist
        dependency-type: direct:development
        update-type: version-update:semver-major
      ...
      Signed-off-by: 's avatardependabot[bot] <support@github.com>
      1651c1cc
    • Robert Knight's avatar
      Improve a couple of code comments · 802828af
      Robert Knight authored
      Improve a few code comments and follow the convention of using
      destructing for constructors that take a single `options` argument.
      802828af
    • Robert Knight's avatar
      Move PDFJSConfig typedef to top of file · 0f3a1295
      Robert Knight authored
      Its easier to scan the file if the typedef comes before references to
      it.
      
      I also reworded and fixed a grammar issue in another comment.
      0f3a1295
    • Robert Knight's avatar
      Rewrite `getPageTextContent` to clarify sync vs async behavior · 3a0d6337
      Robert Knight authored
      An important aspect of this function is that although it returns an
      async result, it populates the cache synchronously, so that two racing
      calls to `getPageTextContent` for the same page don't ask PDF.js to
      extract the same text twice. Add comments to make that clear and remove
      the `async` from the outer function.
      
       - Combine the two internal async helpers into one with no arguments.
         This eliminates some untyped parameters.
      
       - Move the documentation about returned text matching text layer from
         an internal comment to the function's JSDoc, since it is something
         callers need to know even if they don't care about the
         implementation.
      3a0d6337
    • Robert Knight's avatar
      Add test to cover changes in text rendering between PDF.js versions · f7346842
      Robert Knight authored
      Add tests that simulate the different handling of whitespace-only text
      items between older (< v2.9.359) and newer PDF.js releases and check
      that describing and anchoring selectors works in both cases.
      f7346842
    • Robert Knight's avatar
      Fix incorrect anchoring in new PDF.js releases · 8e288390
      Robert Knight authored
      Fix anchoring of text quotes and positions in PDF.js releases (>=
      2.9.359) that include https://github.com/mozilla/pdf.js/pull/13257.
      
      The client's anchoring relies on the text content of pages extracted via
      PDF.js's text APIs (`PDFPage.getTextContent`) to match the `textContent`
      of the hidden text layer element. In older PDF.js releases acheiving
      this alignment required excluding text items with all-whitespace text,
      because PDF.js did not create elements in the text layer for these. In
      PDF.js releases after https://github.com/mozilla/pdf.js/pull/13257 this
      filtering is no longer needed.
      
      The fix in this commit is to feature-detect whether the active version
      of PDF.js includes this change or not and filter or not filter text
      items accordingly.
      
      Future changes to PDF.js could cause mismatches between the result of
      `PDFPage.getTextContent` and the rendered text layer in other ways, so a
      sanity check has been added which logs a console warning if a mismatch
      is detected.
      8e288390
    • Robert Knight's avatar
      Remove an incorrect `checkQuote` helper which worked by accident · bcc1db6e
      Robert Knight authored
      The `checkQuote` helper's code suggested that it was expected to be
      passed a range. However it was being called with a string. This happened
      to work because the implementation only used the `toString` method,
      which exists in both Range objects and strings.
      bcc1db6e
  7. 30 Aug, 2021 6 commits