2 Import bookmarks with keyword from exported firefox bookmarks
Gold Holk edited this page 2022-03-14 21:40:09 +08:00

Though firefox's WebExtension API does not support accessing bookmark's keyword, one can still export all bookmarks to a JSON file, and parse its content to generate searchurls for tridactyl.

Export firefox bookmarks

Firefox's Library can export all bookmarks to a JSON file. To open Library: Toolbox > Bookmarks > Manage Bookmarks or Ctrl-Shift-o .

Click Import and Backup > Backup , and you will get the JSON file.

Import JSON file

Here is the uglified one-line script:

:js (async function(){var d=document,b=d.body;function create(tag,parent){const elm=(parent||b).appendChild(d.createElement(tag));return elm}const file=await promptFile();const text=await blobToText(file);const json=JSON.parse(text);const keywordList=findKeyword(json);const rc=keywordList.map(m=>`set searchurls.${m.keyword} ${m.uri}`).join("\n");window.rc=rc;return source("--url","data:text/plain,"+encodeURIComponent(rc));function promptFile(){return new Promise(ok=>{const input=create("input");input.type="file";input.oninput=(event=>{const file=event.target.files[0];if(file){ok(file);sleep(1).then(()=>input.remove())}else sleep(1).then(()=>event.target.click())});input.click()})}function sleep(second){return new Promise(wake=>setTimeout(wake,second*1e3))}function blobToText(blob){return new Promise(ok=>{const reader=new FileReader;reader.onload=(event=>ok(event.target.result));reader.readAsText(blob)})}function findKeyword(json){const list=[];if(Array.isArray(json.children)){for(const child of json.children){list.push(...findKeyword(child))}}if(json.uri&&json.keyword)list.push({uri:json.uri,keyword:json.keyword});return list}})();

This script will use <input type="file"> for user to input file, and find bookmarks with keyword; finally add them to searchurls.

The non-compress script:

(async function() {
  var d = document,
      b = d.body;

  function create(tag, parent) {
    const elm = (parent || b).appendChild( d.createElement(tag) );
    return elm;
  }

  const file = await promptFile()
  const text = await blobToText(file)
  const json = JSON.parse(text)
  const keywordList = findKeyword(json)
  const rc = keywordList.map(m => `set searchurls.${m.keyword} ${m.uri}`).join('\n')
  window.rc = rc
  return source('--url', 'data:text/plain,' + encodeURIComponent(rc))
  
  function promptFile() {
    return new Promise(ok => {
      const input = create('input')
      input.type = 'file'
      input.oninput = event => {
        const file = event.target.files[0]
        if (file) {
          ok(file)
          sleep(1).then(() => input.remove())
        }
        else sleep(1).then(() => event.target.click())
      }
      input.click()
    })
  }
  function sleep(second) {
    return new Promise(wake => setTimeout(wake, second*1000))
  }
  function blobToText(blob) {
    return new Promise(ok => {
      const reader = new FileReader()
      reader.onload = event => ok(event.target.result)
      reader.readAsText(blob)
    })
  }
  function findKeyword(json) {
    const list = []
    if (Array.isArray(json.children)) {
      for (const child of json.children) {
        list.push(...findKeyword(child))
      }
    }
    if (json.uri && json.keyword) list.push({uri: json.uri, keyword: json.keyword})
    return list
  }
})()