├── .gitignore ├── CHANGELOG.md ├── LICENSE ├── README.md ├── bin └── hardcider.js ├── demo.gif ├── lib └── fetch.js ├── package-lock.json └── package.json /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | node_modules/ 3 | dist/ 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | test/unit/coverage 8 | test/e2e/reports 9 | selenium-debug.log 10 | .idea 11 | .vscode 12 | *.suo 13 | *.ntvs* 14 | *.njsproj 15 | *.sln 16 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | ### v0.3.0 2 | 3 | #### Features 4 | * Added support for [BibTeX](http://www.bibtex.org/) citation format 5 | 6 | #### Fixes 7 | * Fixed embarassing bug where `mla` was hard-coded as the format for book and website citations 8 | 9 | #### Documentation 10 | * Added `CHANGELOG.md` 11 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Alexander Schwartzberg 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # hardcider 2 | :beer: Create citations from the command line 3 | 4 |

5 | Downloads 6 | Version 7 | License 8 |

9 | 10 | 11 | 12 | 13 | ### Installation 14 | Run the following command to install `hardcider` - requires Node.js 8.x and higher 15 | 16 | ```shell 17 | npm install -g hardcider 18 | ``` 19 | 20 | 21 | ### Usage 22 | 23 | - **`hardcider website `** - create a website citation from a URL 24 | 25 | - **`hardcider book `** - create a book citation from an ISBN-10 or ISBN-13 26 | 27 | 28 | ### Example 29 | 30 | ```shell 31 | $ hardcider website --mla https://en.wikipedia.org/wiki/John_Coltrane 32 | 33 | Fetching MLA citation... 34 | 35 | “John Coltrane.” Wikipedia, Wikimedia Foundation, 24 Oct. 2018, en.wikipedia.org/wiki/John_Coltrane. 36 | ``` 37 | 38 | 39 | **Flags** 40 | 41 | The following flags apply to both the `website` and `book` commands 42 | 43 | - `--mla` - returns an [MLA](https://owl.purdue.edu/owl/research_and_citation/mla_style/mla_style_introduction.html) Formatted Citation (default) 44 | - `--apa` - returns an [APA](https://owl.purdue.edu/owl/research_and_citation/apa_style/apa_style_introduction.html) Formatted Citation 45 | - `--chicago` - returns a [Chicago](https://www.chicagomanualofstyle.org/home.html) Formatted Citation 46 | - `--ieee` - returns an [IEEE](https://pitt.libguides.com/citationhelp/ieee) Formatted Citation 47 | - `--bibtex` - returns an [BibTeX](http://www.bibtex.org/) Formatted Citation 48 | 49 | 50 | ### Thanks 51 | 52 | Built with [commanderjs](https://github.com/tj/commander.js/), [chalk](https://github.com/chalk/chalk), [puppeteer](https://github.com/GoogleChrome/puppeteer/), and [citationmachine.net](http://www.citationmachine.net/). Open Source under the [MIT License](https://opensource.org/licenses/MIT). 53 | 54 | 55 | ### Note 56 | 57 | This implementation uses [puppeteer](https://github.com/GoogleChrome/puppeteer/), a headless Chromium browser to navigate through a series of forms on [citationmachine.net](http://www.citationmachine.net/). It's faster than manually using any citation website I've come across, but it's admittedly a resource-intensive approach. -------------------------------------------------------------------------------- /bin/hardcider.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | const chalk = require('chalk') 3 | const semver = require('semver') 4 | const minimist = require('minimist') 5 | const program = require('commander') 6 | 7 | // // // // 8 | 9 | // Citation URL components 10 | const CITATION_URL_ROOT = 'http://www.citationmachine.net/' 11 | const CITATION_URL_SUFFIX_WEBSITE = '/cite-a-website' 12 | const CITATION_URL_SUFFIX_BOOK = '/cite-a-book' 13 | 14 | // Citation Types 15 | const CITATION_TYPE_WEBSITE = 'WEBSITE' 16 | const CITATION_TYPE_BOOK = 'BOOK' 17 | 18 | // Citation Formats 19 | const FORMAT_APA = 'APA' 20 | const FORMAT_MLA = 'MLA' 21 | const FORMAT_CHICAGO = 'Chicago' 22 | const FORMAT_IEEE = 'IEEE' 23 | const FORMAT_BIBTEX = 'bibtex' 24 | 25 | // buildUrl 26 | // Builds a URL from which the citation is fetched 27 | function buildUrl({ type, format }) { 28 | switch (type) { 29 | case CITATION_TYPE_WEBSITE: 30 | return [CITATION_URL_ROOT, format.toLowerCase(), CITATION_URL_SUFFIX_WEBSITE].join('') 31 | case CITATION_TYPE_BOOK: 32 | return [CITATION_URL_ROOT, format.toLowerCase(), CITATION_URL_SUFFIX_BOOK].join('') 33 | } 34 | } 35 | 36 | // getFormat 37 | // Pulls the correct format from CLI options 38 | function getFormat(options) { 39 | if (options.mla) { return FORMAT_MLA } 40 | if (options.chicago) { return FORMAT_CHICAGO } 41 | if (options.ieee) { return FORMAT_IEEE } 42 | if (options.bibtex) { return FORMAT_BIBTEX } 43 | return FORMAT_APA 44 | } 45 | 46 | // handleResponse 47 | // Returns a response handler function 48 | function handleResponse(format) { 49 | return function(resp) { 50 | 51 | // TODO - pretty-print BibTeX citation here 52 | 53 | // Logs citations 54 | console.log(`\n${chalk.yellow(resp)}\n`) 55 | 56 | // Exit the CLI 57 | process.exit() 58 | } 59 | } 60 | 61 | // // // // 62 | 63 | program 64 | .version(require('../package').version) 65 | .usage(' [options]') 66 | 67 | program 68 | .command('website ') 69 | .description('fetch a basic citation for the website-url argument') 70 | .option('--apa', 'APA Formatted citation (default)') 71 | .option('--mla', 'MLA Formatted citation') 72 | .option('--chicago', 'Chicao Formatted citation') 73 | .option('--ieee', 'IEEE Format citation') 74 | .option('--bibtex', 'BibTeX Format citation') 75 | .action((websiteUrl, cmd) => { 76 | const format = getFormat(cleanArgs(cmd)) 77 | const fetchUrl = buildUrl({ type: CITATION_TYPE_WEBSITE, format: format }) 78 | 79 | // Logs start prompt 80 | console.log(`\n${chalk.blue(`Fetching ${format} website citation...`)}`) 81 | 82 | // Fetch citation 83 | require('../lib/fetch')(fetchUrl, websiteUrl).then(handleResponse(format)) 84 | }) 85 | 86 | program 87 | .command('book ') 88 | .description('fetch a basic citation for the a book\'s ISBN') 89 | .option('--apa', 'APA Formatted citation (default)') 90 | .option('--mla', 'MLA Formatted citation') 91 | .option('--chicago', 'Chicao Formatted citation') 92 | .option('--ieee', 'IEEE Format citation') 93 | .option('--bibtex', 'BibTeX Format citation') 94 | .action((isbn, cmd) => { 95 | const format = getFormat(cleanArgs(cmd)) 96 | const fetchUrl = buildUrl({ type: CITATION_TYPE_BOOK, format: format }) 97 | 98 | // Logs start prompt 99 | console.log(`\n${chalk.blue(`Fetching ${format} book citation...`)}`) 100 | 101 | // Fetch citation 102 | require('../lib/fetch')(fetchUrl, isbn).then(handleResponse(format)) 103 | }) 104 | 105 | // output help information on unknown commands 106 | program 107 | .arguments('') 108 | .action((cmd) => { 109 | program.outputHelp() 110 | console.log(` ` + chalk.red(`Unknown command ${chalk.yellow(cmd)}.`)) 111 | console.log() 112 | }) 113 | 114 | // add some useful info on help 115 | program.on('--help', () => { 116 | console.log() 117 | console.log(` Run ${chalk.cyan(`hardcider --help`)} for detailed usage of given command.`) 118 | console.log() 119 | }) 120 | 121 | program.commands.forEach(c => c.on('--help', () => console.log())) 122 | 123 | // Parse arguments into commander program 124 | program.parse(process.argv) 125 | 126 | if (!process.argv.slice(2).length) { 127 | program.outputHelp() 128 | } 129 | 130 | function camelize (str) { 131 | return str.replace(/-(\w)/g, (_, c) => c ? c.toUpperCase() : '') 132 | } 133 | 134 | // commander passes the Command object itself as options, 135 | // extract only actual options into a fresh object. 136 | function cleanArgs (cmd) { 137 | const args = {} 138 | cmd.options.forEach(o => { 139 | const key = camelize(o.long.replace(/^--/, '')) 140 | // if an option is not present and Command has a method with the same name 141 | // it should not be copied 142 | if (typeof cmd[key] !== 'function' && typeof cmd[key] !== 'undefined') { 143 | args[key] = cmd[key] 144 | } 145 | }) 146 | return args 147 | } 148 | -------------------------------------------------------------------------------- /demo.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/aeksco/hardcider/a844abc2a0072b30b1db374590fee913768c5e68/demo.gif -------------------------------------------------------------------------------- /lib/fetch.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | const puppeteer = require('puppeteer'); 3 | const HEADLESS = true // NOTE - change to `false` for dubugging 4 | 5 | // Options for Puppeteer headless browser 6 | const PUPPETEER_OPTIONS = { 7 | headless: HEADLESS, 8 | slowMo: 5, 9 | args: [ 10 | '--no-sandbox', 11 | '--disable-setuid-sandbox', 12 | '--enable-logging', 13 | '--v=1' 14 | ] 15 | } 16 | 17 | // fetchCitation 18 | // Fetches an individual citation from the server 19 | module.exports = async function fetchCitation(citation_url, query) { 20 | 21 | // Instantiates new headless browser 22 | const browser = await puppeteer.launch(PUPPETEER_OPTIONS); 23 | 24 | // Navigates to citation_url 25 | const page = await browser.newPage(); 26 | await page._client.send('Page.setDownloadBehavior', { behavior: 'allow', downloadPath: './' }) 27 | await page.goto(citation_url, { waitUntil: 'domcontentloaded' }); 28 | 29 | // Submitting form 30 | await page.waitFor('input[name=q]') 31 | await page.$eval('input[name=q]', (el, value) => el.value = value, query); 32 | await page.click('input[name=commit]'); 33 | 34 | // Waiting for next page load 35 | await page.waitFor('button.select-result[type=submit]'); 36 | await page.click('button.select-result[type=submit]'); 37 | 38 | // Clicking "Final Step" button 39 | await page.waitFor('[alt="continue to final step"]'); 40 | await page.click('[alt="continue to final step"]'); 41 | 42 | // Clicking "Create Citation" button 43 | await page.waitFor('#create_citation'); 44 | await page.click('#create_citation'); 45 | 46 | // Waits for the DOM element that wraps the good stuff 47 | await page.waitFor('.bibliography-item-copy-text'); 48 | 49 | // Isolates the element with the citation's text content 50 | // and pulls the citation text out of it 51 | const element = await page.$('.bibliography-item.most-recent') 52 | const citationText = await element.$eval('.bibliography-item-copy-text', node => node.innerText); 53 | 54 | // Closes the browser 55 | await browser.close(); 56 | 57 | // Returns the inner text 58 | return citationText 59 | } 60 | -------------------------------------------------------------------------------- /package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "hardcider", 3 | "version": "0.1.0", 4 | "lockfileVersion": 1, 5 | "requires": true, 6 | "dependencies": { 7 | "agent-base": { 8 | "version": "4.2.1", 9 | "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.2.1.tgz", 10 | "integrity": "sha512-JVwXMr9nHYTUXsBFKUqhJwvlcYU/blreOEUkhNR2eXZIvwd+c+o5V4MgDPKWnMS/56awN3TRzIP+KoPn+roQtg==", 11 | "requires": { 12 | "es6-promisify": "5.0.0" 13 | } 14 | }, 15 | "ansi-escapes": { 16 | "version": "3.1.0", 17 | "resolved": "http://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", 18 | "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==" 19 | }, 20 | "ansi-regex": { 21 | "version": "3.0.0", 22 | "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", 23 | "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" 24 | }, 25 | "ansi-styles": { 26 | "version": "3.2.1", 27 | "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", 28 | "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", 29 | "requires": { 30 | "color-convert": "1.9.3" 31 | } 32 | }, 33 | "async-limiter": { 34 | "version": "1.0.0", 35 | "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", 36 | "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" 37 | }, 38 | "balanced-match": { 39 | "version": "1.0.0", 40 | "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", 41 | "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" 42 | }, 43 | "brace-expansion": { 44 | "version": "1.1.11", 45 | "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", 46 | "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", 47 | "requires": { 48 | "balanced-match": "1.0.0", 49 | "concat-map": "0.0.1" 50 | } 51 | }, 52 | "buffer-from": { 53 | "version": "1.1.1", 54 | "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", 55 | "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==" 56 | }, 57 | "chalk": { 58 | "version": "2.4.1", 59 | "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.1.tgz", 60 | "integrity": "sha512-ObN6h1v2fTJSmUXoS3nMQ92LbDK9be4TV+6G+omQlGJFdcUX5heKi1LZ1YnRMIgwTLEj3E24bT6tYni50rlCfQ==", 61 | "requires": { 62 | "ansi-styles": "3.2.1", 63 | "escape-string-regexp": "1.0.5", 64 | "supports-color": "5.5.0" 65 | } 66 | }, 67 | "chardet": { 68 | "version": "0.7.0", 69 | "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", 70 | "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==" 71 | }, 72 | "cli-cursor": { 73 | "version": "2.1.0", 74 | "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", 75 | "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", 76 | "requires": { 77 | "restore-cursor": "2.0.0" 78 | } 79 | }, 80 | "cli-width": { 81 | "version": "2.2.0", 82 | "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", 83 | "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=" 84 | }, 85 | "color-convert": { 86 | "version": "1.9.3", 87 | "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", 88 | "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", 89 | "requires": { 90 | "color-name": "1.1.3" 91 | } 92 | }, 93 | "color-name": { 94 | "version": "1.1.3", 95 | "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", 96 | "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" 97 | }, 98 | "commander": { 99 | "version": "2.19.0", 100 | "resolved": "https://registry.npmjs.org/commander/-/commander-2.19.0.tgz", 101 | "integrity": "sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==" 102 | }, 103 | "concat-map": { 104 | "version": "0.0.1", 105 | "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", 106 | "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" 107 | }, 108 | "concat-stream": { 109 | "version": "1.6.2", 110 | "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", 111 | "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", 112 | "requires": { 113 | "buffer-from": "1.1.1", 114 | "inherits": "2.0.3", 115 | "readable-stream": "2.3.6", 116 | "typedarray": "0.0.6" 117 | } 118 | }, 119 | "core-util-is": { 120 | "version": "1.0.2", 121 | "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", 122 | "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" 123 | }, 124 | "debug": { 125 | "version": "2.6.9", 126 | "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", 127 | "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", 128 | "requires": { 129 | "ms": "2.0.0" 130 | } 131 | }, 132 | "es6-promise": { 133 | "version": "4.2.4", 134 | "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.4.tgz", 135 | "integrity": "sha512-/NdNZVJg+uZgtm9eS3O6lrOLYmQag2DjdEXuPaHlZ6RuVqgqaVZfgYCepEIKsLqwdQArOPtC3XzRLqGGfT8KQQ==" 136 | }, 137 | "es6-promisify": { 138 | "version": "5.0.0", 139 | "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz", 140 | "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=", 141 | "requires": { 142 | "es6-promise": "4.2.4" 143 | } 144 | }, 145 | "escape-string-regexp": { 146 | "version": "1.0.5", 147 | "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", 148 | "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" 149 | }, 150 | "external-editor": { 151 | "version": "3.0.3", 152 | "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.0.3.tgz", 153 | "integrity": "sha512-bn71H9+qWoOQKyZDo25mOMVpSmXROAsTJVVVYzrrtol3d4y+AsKjf4Iwl2Q+IuT0kFSQ1qo166UuIwqYq7mGnA==", 154 | "requires": { 155 | "chardet": "0.7.0", 156 | "iconv-lite": "0.4.24", 157 | "tmp": "0.0.33" 158 | } 159 | }, 160 | "extract-zip": { 161 | "version": "1.6.7", 162 | "resolved": "https://registry.npmjs.org/extract-zip/-/extract-zip-1.6.7.tgz", 163 | "integrity": "sha1-qEC0uK9kAyZMjbV/Txp0Mz74H+k=", 164 | "requires": { 165 | "concat-stream": "1.6.2", 166 | "debug": "2.6.9", 167 | "mkdirp": "0.5.1", 168 | "yauzl": "2.4.1" 169 | } 170 | }, 171 | "fd-slicer": { 172 | "version": "1.0.1", 173 | "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", 174 | "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", 175 | "requires": { 176 | "pend": "1.2.0" 177 | } 178 | }, 179 | "figures": { 180 | "version": "2.0.0", 181 | "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", 182 | "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", 183 | "requires": { 184 | "escape-string-regexp": "1.0.5" 185 | } 186 | }, 187 | "fs.realpath": { 188 | "version": "1.0.0", 189 | "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", 190 | "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" 191 | }, 192 | "glob": { 193 | "version": "7.1.3", 194 | "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", 195 | "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", 196 | "requires": { 197 | "fs.realpath": "1.0.0", 198 | "inflight": "1.0.6", 199 | "inherits": "2.0.3", 200 | "minimatch": "3.0.4", 201 | "once": "1.4.0", 202 | "path-is-absolute": "1.0.1" 203 | } 204 | }, 205 | "has-flag": { 206 | "version": "3.0.0", 207 | "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", 208 | "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" 209 | }, 210 | "https-proxy-agent": { 211 | "version": "2.2.1", 212 | "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.1.tgz", 213 | "integrity": "sha512-HPCTS1LW51bcyMYbxUIOO4HEOlQ1/1qRaFWcyxvwaqUS9TY88aoEuHUY33kuAh1YhVVaDQhLZsnPd+XNARWZlQ==", 214 | "requires": { 215 | "agent-base": "4.2.1", 216 | "debug": "3.1.0" 217 | }, 218 | "dependencies": { 219 | "debug": { 220 | "version": "3.1.0", 221 | "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", 222 | "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", 223 | "requires": { 224 | "ms": "2.0.0" 225 | } 226 | } 227 | } 228 | }, 229 | "iconv-lite": { 230 | "version": "0.4.24", 231 | "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", 232 | "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", 233 | "requires": { 234 | "safer-buffer": "2.1.2" 235 | } 236 | }, 237 | "inflight": { 238 | "version": "1.0.6", 239 | "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", 240 | "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", 241 | "requires": { 242 | "once": "1.4.0", 243 | "wrappy": "1.0.2" 244 | } 245 | }, 246 | "inherits": { 247 | "version": "2.0.3", 248 | "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", 249 | "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" 250 | }, 251 | "inquirer": { 252 | "version": "6.2.0", 253 | "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.0.tgz", 254 | "integrity": "sha512-QIEQG4YyQ2UYZGDC4srMZ7BjHOmNk1lR2JQj5UknBapklm6WHA+VVH7N+sUdX3A7NeCfGF8o4X1S3Ao7nAcIeg==", 255 | "requires": { 256 | "ansi-escapes": "3.1.0", 257 | "chalk": "2.4.1", 258 | "cli-cursor": "2.1.0", 259 | "cli-width": "2.2.0", 260 | "external-editor": "3.0.3", 261 | "figures": "2.0.0", 262 | "lodash": "4.17.11", 263 | "mute-stream": "0.0.7", 264 | "run-async": "2.3.0", 265 | "rxjs": "6.3.3", 266 | "string-width": "2.1.1", 267 | "strip-ansi": "4.0.0", 268 | "through": "2.3.8" 269 | } 270 | }, 271 | "is-fullwidth-code-point": { 272 | "version": "2.0.0", 273 | "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", 274 | "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" 275 | }, 276 | "is-promise": { 277 | "version": "2.1.0", 278 | "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", 279 | "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=" 280 | }, 281 | "isarray": { 282 | "version": "1.0.0", 283 | "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", 284 | "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" 285 | }, 286 | "lodash": { 287 | "version": "4.17.11", 288 | "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", 289 | "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==" 290 | }, 291 | "mimic-fn": { 292 | "version": "1.2.0", 293 | "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", 294 | "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" 295 | }, 296 | "minimatch": { 297 | "version": "3.0.4", 298 | "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", 299 | "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", 300 | "requires": { 301 | "brace-expansion": "1.1.11" 302 | } 303 | }, 304 | "minimist": { 305 | "version": "1.2.0", 306 | "resolved": "http://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", 307 | "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" 308 | }, 309 | "mkdirp": { 310 | "version": "0.5.1", 311 | "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", 312 | "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", 313 | "requires": { 314 | "minimist": "0.0.8" 315 | }, 316 | "dependencies": { 317 | "minimist": { 318 | "version": "0.0.8", 319 | "resolved": "http://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", 320 | "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" 321 | } 322 | } 323 | }, 324 | "ms": { 325 | "version": "2.0.0", 326 | "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", 327 | "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" 328 | }, 329 | "mute-stream": { 330 | "version": "0.0.7", 331 | "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", 332 | "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=" 333 | }, 334 | "once": { 335 | "version": "1.4.0", 336 | "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", 337 | "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", 338 | "requires": { 339 | "wrappy": "1.0.2" 340 | } 341 | }, 342 | "onetime": { 343 | "version": "2.0.1", 344 | "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", 345 | "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", 346 | "requires": { 347 | "mimic-fn": "1.2.0" 348 | } 349 | }, 350 | "os-tmpdir": { 351 | "version": "1.0.2", 352 | "resolved": "http://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", 353 | "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" 354 | }, 355 | "path-is-absolute": { 356 | "version": "1.0.1", 357 | "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", 358 | "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" 359 | }, 360 | "pend": { 361 | "version": "1.2.0", 362 | "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", 363 | "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=" 364 | }, 365 | "process-nextick-args": { 366 | "version": "2.0.0", 367 | "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", 368 | "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" 369 | }, 370 | "progress": { 371 | "version": "2.0.0", 372 | "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.0.tgz", 373 | "integrity": "sha1-ihvjZr+Pwj2yvSPxDG/pILQ4nR8=" 374 | }, 375 | "proxy-from-env": { 376 | "version": "1.0.0", 377 | "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.0.0.tgz", 378 | "integrity": "sha1-M8UDmPcOp+uW0h97gXYwpVeRx+4=" 379 | }, 380 | "puppeteer": { 381 | "version": "1.7.0", 382 | "resolved": "https://registry.npmjs.org/puppeteer/-/puppeteer-1.7.0.tgz", 383 | "integrity": "sha512-f+1DxKHPqce6CXUBz2eVO2WcATeVeQSOPG9GYaGObEZDCiCEUwG+gogjMsrvn7he2wHTqNVb5p6RUrwmr8XFBA==", 384 | "requires": { 385 | "debug": "3.1.0", 386 | "extract-zip": "1.6.7", 387 | "https-proxy-agent": "2.2.1", 388 | "mime": "2.3.1", 389 | "progress": "2.0.0", 390 | "proxy-from-env": "1.0.0", 391 | "rimraf": "2.6.2", 392 | "ws": "5.2.2" 393 | }, 394 | "dependencies": { 395 | "debug": { 396 | "version": "3.1.0", 397 | "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", 398 | "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", 399 | "requires": { 400 | "ms": "2.0.0" 401 | } 402 | }, 403 | "mime": { 404 | "version": "2.3.1", 405 | "resolved": "https://registry.npmjs.org/mime/-/mime-2.3.1.tgz", 406 | "integrity": "sha512-OEUllcVoydBHGN1z84yfQDimn58pZNNNXgZlHXSboxMlFvgI6MXSWpWKpFRra7H1HxpVhHTkrghfRW49k6yjeg==" 407 | } 408 | } 409 | }, 410 | "readable-stream": { 411 | "version": "2.3.6", 412 | "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", 413 | "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", 414 | "requires": { 415 | "core-util-is": "1.0.2", 416 | "inherits": "2.0.3", 417 | "isarray": "1.0.0", 418 | "process-nextick-args": "2.0.0", 419 | "safe-buffer": "5.1.1", 420 | "string_decoder": "1.1.1", 421 | "util-deprecate": "1.0.2" 422 | } 423 | }, 424 | "restore-cursor": { 425 | "version": "2.0.0", 426 | "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", 427 | "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", 428 | "requires": { 429 | "onetime": "2.0.1", 430 | "signal-exit": "3.0.2" 431 | } 432 | }, 433 | "rimraf": { 434 | "version": "2.6.2", 435 | "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", 436 | "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", 437 | "requires": { 438 | "glob": "7.1.3" 439 | } 440 | }, 441 | "run-async": { 442 | "version": "2.3.0", 443 | "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", 444 | "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", 445 | "requires": { 446 | "is-promise": "2.1.0" 447 | } 448 | }, 449 | "rxjs": { 450 | "version": "6.3.3", 451 | "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.3.3.tgz", 452 | "integrity": "sha512-JTWmoY9tWCs7zvIk/CvRjhjGaOd+OVBM987mxFo+OW66cGpdKjZcpmc74ES1sB//7Kl/PAe8+wEakuhG4pcgOw==", 453 | "requires": { 454 | "tslib": "1.9.3" 455 | } 456 | }, 457 | "safe-buffer": { 458 | "version": "5.1.1", 459 | "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", 460 | "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" 461 | }, 462 | "safer-buffer": { 463 | "version": "2.1.2", 464 | "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", 465 | "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" 466 | }, 467 | "semver": { 468 | "version": "5.6.0", 469 | "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", 470 | "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" 471 | }, 472 | "signal-exit": { 473 | "version": "3.0.2", 474 | "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", 475 | "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" 476 | }, 477 | "string-width": { 478 | "version": "2.1.1", 479 | "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", 480 | "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", 481 | "requires": { 482 | "is-fullwidth-code-point": "2.0.0", 483 | "strip-ansi": "4.0.0" 484 | } 485 | }, 486 | "string_decoder": { 487 | "version": "1.1.1", 488 | "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", 489 | "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", 490 | "requires": { 491 | "safe-buffer": "5.1.1" 492 | } 493 | }, 494 | "strip-ansi": { 495 | "version": "4.0.0", 496 | "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", 497 | "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", 498 | "requires": { 499 | "ansi-regex": "3.0.0" 500 | } 501 | }, 502 | "supports-color": { 503 | "version": "5.5.0", 504 | "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", 505 | "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", 506 | "requires": { 507 | "has-flag": "3.0.0" 508 | } 509 | }, 510 | "through": { 511 | "version": "2.3.8", 512 | "resolved": "http://registry.npmjs.org/through/-/through-2.3.8.tgz", 513 | "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" 514 | }, 515 | "tmp": { 516 | "version": "0.0.33", 517 | "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", 518 | "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", 519 | "requires": { 520 | "os-tmpdir": "1.0.2" 521 | } 522 | }, 523 | "tslib": { 524 | "version": "1.9.3", 525 | "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.9.3.tgz", 526 | "integrity": "sha512-4krF8scpejhaOgqzBEcGM7yDIEfi0/8+8zDRZhNZZ2kjmHJ4hv3zCbQWxoJGz1iw5U0Jl0nma13xzHXcncMavQ==" 527 | }, 528 | "typedarray": { 529 | "version": "0.0.6", 530 | "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", 531 | "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=" 532 | }, 533 | "util-deprecate": { 534 | "version": "1.0.2", 535 | "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", 536 | "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" 537 | }, 538 | "wrappy": { 539 | "version": "1.0.2", 540 | "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", 541 | "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" 542 | }, 543 | "ws": { 544 | "version": "5.2.2", 545 | "resolved": "https://registry.npmjs.org/ws/-/ws-5.2.2.tgz", 546 | "integrity": "sha512-jaHFD6PFv6UgoIVda6qZllptQsMlDEJkTQcybzzXDYM1XO9Y8em691FGMPmM46WGyLU4z9KMgQN+qrux/nhlHA==", 547 | "requires": { 548 | "async-limiter": "1.0.0" 549 | } 550 | }, 551 | "yauzl": { 552 | "version": "2.4.1", 553 | "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.4.1.tgz", 554 | "integrity": "sha1-lSj0QtqxsihOWLQ3m7GU4i4MQAU=", 555 | "requires": { 556 | "fd-slicer": "1.0.1" 557 | } 558 | } 559 | } 560 | } 561 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "hardcider", 3 | "version": "0.3.0", 4 | "description": "CLI for quickly generating citations for websites and books", 5 | "bin": { 6 | "hardcider": "bin/hardcider.js" 7 | }, 8 | "homepage": "https://github.com/aeksco/hardcider#readme", 9 | "repository": { 10 | "type": "git", 11 | "url": "git+https://github.com/aeksco/hardcider.git" 12 | }, 13 | "bugs": { 14 | "url": "https://github.com/aeksco/hardcider/issues" 15 | }, 16 | "author": "", 17 | "keywords": [ 18 | "Citation", 19 | "CLI", 20 | "MLA", 21 | "IEEE", 22 | "BibTeX", 23 | "Bibliography" 24 | ], 25 | "license": "MIT", 26 | "dependencies": { 27 | "puppeteer": "^1.7.0", 28 | "chalk": "^2.4.1", 29 | "commander": "^2.19.0", 30 | "inquirer": "^6.2.0", 31 | "minimist": "^1.2.0", 32 | "semver": "^5.6.0" 33 | }, 34 | "engines": { 35 | "node": ">=8.9" 36 | } 37 | } 38 | --------------------------------------------------------------------------------