title: Can't use crypto in NPM dependency in Electron app
body: <p>I'm building an Electron app (with Ionic) to digitally sign PDFs with p12 certificates using node-signpdf (<a href="https://www.npmjs.com/package/node-signpdf" rel="nofollow noreferrer">https://www.npmjs.com/package/node-signpdf</a>). I've had problems which I solved by using <code>require ('electron').remote</code> for example for <code>fs</code>.</p>
  
  <p>I've also installed the same node version in my OS (MacOS Catalina) as the same one that electron is using (Node v12.4.0).</p>
  
  <p>The problem is that one of the NPM dependencies uses crypto and it shows as undefined with the next error:</p>
  
  <pre><code>HomePage.html:39 ERROR TypeError: _crypto.randomBytes is not a function
      at Object.ctx.seedFileSync (prng.js:340)
      at _reseedSync (prng.js:210)
      at Object.ctx.generateSync (prng.js:163)
      at Object.ctx.generate (prng.js:80)
      at Object.ctx.getBytes (random.js:92)
      at _modPow (rsa.js:431)
      at Object.push../node_modules/node-forge/lib/rsa.js.pki.rsa.encrypt (rsa.js:501)
      at Object.key.sign (rsa.js:1245)
      at addSignerInfos (pkcs7.js:534)
      at Object.sign (pkcs7.js:377)
  </code></pre>
  
  <p>What I can see is that <code>node-signpdf</code> uses <code>node-forge</code> as a dependency, and <code>node-forge</code> loads crypto inside <code>prng.js</code> this way:</p>
  
  <pre><code>var _crypto = null;
  if(forge.util.isNodejs &amp;&amp; !forge.options.usePureJavaScript &amp;&amp;
    !process.versions['node-webkit']) {
    _crypto = require('crypto');
  }
  </code></pre>
  
  <p>I've tried changing that part of the code to use crypto-js or browserfy-crypto (this last one doesn't even build and hasn't been updated in years), but I keep getting the error shown above.</p>
  
  <p><strong>EDIT 1</strong>:
  This is how I'm implementing the signature in my service:</p>
  
  <pre><code>public signFile(pathToFile: string, pathToCert: string): void {
  const fs = (&lt;any&gt;window).require('fs');
  
  let certBuffer = fs.readFileSync(pathToCert);
  let fileBuffer = fs.readFileSync(pathToFile);
  
  fileBuffer = plainAddPlaceholder({
    pdfBuffer: fileBuffer,
    reason: 'I have reviewed it.',
    signatureLength: 1612,
  });
  const signedPdf = signer.sign(fileBuffer, certBuffer, {passphrase: 'qwertyui'});
  }
  </code></pre>
  
  <p>The code adds the placeholder to add the signature, the problem comes in <code>signer.sign</code></p>
  
  <p><strong>EDIT 2</strong>:</p>
  
  <p>When I run the app if I type in console: <code>require ('crypto')</code> I see the methods, so it looks like it's loaded in the global scope,  the problem seems to be in the NPM dependency of <code>node-forge</code>.</p>
  
  <p><strong>EDIT 3</strong>:</p>
  
  <p>I've changed <code>require('crypto')</code> to <code>window.require('crypto')</code> and started working. But I think I'll have to make postinstall script to modify it.</p>
  
  <p>Is there a better way?</p>
  
  <p>-</p>
  
  <p>How can I make this crypto thing work? I ran out of ideas. Maybe you can spare some?</p>
  
  <p>Thanks for your time!</p>