title: Uncaught URIError: URI malformed error with jQuery
body: <p>I'm using <a href="https://www.npmjs.com/package/node-forge#aes" rel="nofollow noreferrer">node forge</a> to encrypt a form before sending it to the server using <a href="https://www.npmjs.com/package/node-forge#aes" rel="nofollow noreferrer">AES</a>.</p>
  
  <p>The code for the crypto part for now is</p>
  
  <pre><code>const bigInt = require("big-integer");
  const forge = require('node-forge');
  
  function generateParams() {
      // Cryptographic random number generator
      var array = new Uint32Array(2);
      var _key = bigInt(window.crypto.getRandomValues(array)[0]).toString();
      var _iv = bigInt(window.crypto.getRandomValues(array)[1]).toString();
      // generate random key and IV 
      var key = forge.util.encode64(_key);
      var iv = forge.util.encode64(_iv);
      const params = {
          key: key,
          iv: iv
      }
      return params;
  }
  
  function encrypt(params) {
      var cipher = forge.rc2.createEncryptionCipher(params.key);
      cipher.start(params.iv);
      // Encrypting "testing"
      cipher.update(forge.util.createBuffer("testing"));
      cipher.finish();
      return cipher.output;
  }
  
  function decrypt(params, encrypted) {
      var cipher = forge.rc2.createDecryptionCipher(params.key);
      cipher.start(params.iv);
      cipher.update(encrypted);
      cipher.finish();
      return cipher.output;
  }
  </code></pre>
  
  <p>and the jQuery function is (not posting yet)</p>
  
  <pre><code>$('#recordForm').submit(function(event) {
      // Stop form from submitting normally
      event.preventDefault();
      // Grab form data
      // Crypto
      const params = generateParams();
      const encryptedForm = {
          test: encrypt(params),
      }
      console.log("Encrypted: " + encryptedForm.test);
      const decryptedForm = {
          test: decrypt(params, encryptedForm.id).data,
      }
      console.log("Decrypted: " + decryptedForm.test);
  });
  </code></pre>
  
  <p>My problem is that I keep getting back (cryptob.js is the name of my file, generated with browserify)</p>
  
  <pre><code>Uncaught URIError: URI malformed
      at decodeURIComponent (&lt;anonymous&gt;)
      at Object.util.decodeUtf8 (cryptob.js:24437)
      at ByteStringBuffer.util.ByteStringBuffer.toString (cryptob.js:23490)
      at HTMLFormElement.&lt;anonymous&gt; (cryptob.js:1282)
      at HTMLFormElement.dispatch (jquery-3.1.1.slim.min.js:3)
      at HTMLFormElement.q.handle (jquery-3.1.1.slim.min.js:3)
  </code></pre>
  
  <p>when calling <code>encrypt()</code>.</p>
  
  <p>There is <a href="https://stackoverflow.com/questions/15326777/uncaught-urierror-uri-malformed-jquery-ui-tabs-on-windows#16639042">this</a> answer here which recommends including a special meta tag. I have done that but it still doesn't work. Since some resources online say it is related to UTF-8 encoding, I tried replacing </p>
  
  <pre><code>cipher.update(forge.util.createBuffer("testing"));
  </code></pre>
  
  <p>with</p>
  
  <pre><code>cipher.update(forge.util.createBuffer(encodeURIComponent("testing")));
  </code></pre>
  
  <p>or </p>
  
  <pre><code>cipher.update(forge.util.createBuffer("testing", 'utf8'));
  </code></pre>
  
  <p>but it didn't work either (based on <a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/encodeURIComponent" rel="nofollow noreferrer">encodeURIComponent(str)</a>).</p>
  
  <p>You can test forge <a href="https://npm.runkit.com/node-forge#aes" rel="nofollow noreferrer">here</a>, and if you run this code (which is essentially what I'm doing)</p>
  
  <pre><code>var forge = require("node-forge")
  
  // generate a random key and IV 
  var key = forge.util.encode64("12354523465");
  var iv = forge.util.encode64("2315");
  
  // encrypt some bytes 
  var cipher = forge.rc2.createEncryptionCipher(key);
  cipher.start(iv);
  cipher.update(forge.util.createBuffer("testing"));
  cipher.finish();
  var encrypted = cipher.output; 
  console.log(encrypted);
  
  // decrypt some bytes 
  var cipher = forge.rc2.createDecryptionCipher(key);
  cipher.start(iv);
  cipher.update(encrypted);
  cipher.finish();
  console.log(cipher.output.data)
  </code></pre>
  
  <p>it works fine. </p>
  
  <p>How can I solve this?</p>