├── .gitattributes ├── .github └── ISSUE_TEMPLATE │ ├── bug-report.md │ └── feature-request.md ├── .gitignore ├── CODE_OF_CONDUCT.md ├── LICENSE ├── README.md ├── api.js ├── assets ├── blog │ ├── blog.json │ └── blogTemplate.html ├── index.css ├── index.html ├── service-worker.js └── themes │ ├── dark.css │ └── light.css ├── bin └── gitfolio.js ├── build.js ├── default ├── blog.json └── config.json ├── package-lock.json ├── package.json ├── populate.js ├── run.js ├── ui.js ├── update.js ├── utils.js └── views ├── blog.ejs ├── css ├── font │ └── Circular.otf └── index.css └── index.ejs /.gitattributes: -------------------------------------------------------------------------------- 1 | # Set the default behavior, in case people don't have core.autocrlf set 2 | * text=auto 3 | 4 | # Require Unix line endings 5 | * text eol=lf -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug-report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🐛 Bug Report 3 | about: Report a bug in the project. 4 | --- 5 | 6 |
7 | System Information 8 | 9 | 10 | 11 | | Name | Value | 12 | | --------------- | -------------------------------------------------------------- | 13 | | OS | Mac/Windows/Linux | 14 | | Node Version | | 15 | | Project Version | | 16 | 17 |
18 | 19 |
20 | What is the current behavior? 21 | 22 | 23 |
24 | 25 |
26 | What is the expected behavior? 27 | 28 | 29 |
30 | 31 |
32 | Logs 33 | 34 | 35 | 36 | ``` 37 | 38 | ``` 39 | 40 |
41 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/feature-request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: ✨ Feature Request 3 | about: Request a new feature. 4 | --- 5 | 6 | # What feature should be added? 7 | 8 | This feature adds Twitter, Linkedin and Medium links to your profile. 9 | 10 | # Why should this feature be added? 11 | 12 | Since a portfolio is being made, adding these links help improve the profile better. 13 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | 8 | # Runtime data 9 | pids 10 | *.pid 11 | *.seed 12 | *.pid.lock 13 | 14 | # Directory for instrumented libs generated by jscoverage/JSCover 15 | lib-cov 16 | 17 | # Coverage directory used by tools like istanbul 18 | coverage 19 | 20 | # nyc test coverage 21 | .nyc_output 22 | 23 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 24 | .grunt 25 | 26 | # Bower dependency directory (https://bower.io/) 27 | bower_components 28 | 29 | # node-waf configuration 30 | .lock-wscript 31 | 32 | # Compiled binary addons (https://nodejs.org/api/addons.html) 33 | build/Release 34 | 35 | # Dependency directories 36 | node_modules/ 37 | jspm_packages/ 38 | 39 | # TypeScript v1 declaration files 40 | typings/ 41 | 42 | # Optional npm cache directory 43 | .npm 44 | 45 | # Optional eslint cache 46 | .eslintcache 47 | 48 | # Optional REPL history 49 | .node_repl_history 50 | 51 | # Output of 'npm pack' 52 | *.tgz 53 | 54 | # Yarn Integrity file 55 | .yarn-integrity 56 | 57 | # dotenv environment variables file 58 | .env 59 | 60 | # next.js build output 61 | .next 62 | 63 | # Built website files 64 | dist/ 65 | 66 | # Editor files and folders 67 | .vscode/ 68 | .idea/ 69 | -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | # Contributor Covenant Code of Conduct 2 | 3 | ## Our Pledge 4 | 5 | In the interest of fostering an open and welcoming environment, we as 6 | contributors and maintainers pledge to making participation in our project and 7 | our community a harassment-free experience for everyone, regardless of age, body 8 | size, disability, ethnicity, sex characteristics, gender identity and expression, 9 | level of experience, education, socio-economic status, nationality, personal 10 | appearance, race, religion, or sexual identity and orientation. 11 | 12 | ## Our Standards 13 | 14 | Examples of behavior that contributes to creating a positive environment 15 | include: 16 | 17 | - Using welcoming and inclusive language 18 | - Being respectful of differing viewpoints and experiences 19 | - Gracefully accepting constructive criticism 20 | - Focusing on what is best for the community 21 | - Showing empathy towards other community members 22 | 23 | Examples of unacceptable behavior by participants include: 24 | 25 | - The use of sexualized language or imagery and unwelcome sexual attention or 26 | advances 27 | - Trolling, insulting/derogatory comments, and personal or political attacks 28 | - Public or private harassment 29 | - Publishing others' private information, such as a physical or electronic 30 | address, without explicit permission 31 | - Other conduct which could reasonably be considered inappropriate in a 32 | professional setting 33 | 34 | ## Our Responsibilities 35 | 36 | Project maintainers are responsible for clarifying the standards of acceptable 37 | behavior and are expected to take appropriate and fair corrective action in 38 | response to any instances of unacceptable behavior. 39 | 40 | Project maintainers have the right and responsibility to remove, edit, or 41 | reject comments, commits, code, wiki edits, issues, and other contributions 42 | that are not aligned to this Code of Conduct, or to ban temporarily or 43 | permanently any contributor for other behaviors that they deem inappropriate, 44 | threatening, offensive, or harmful. 45 | 46 | ## Scope 47 | 48 | This Code of Conduct applies both within project spaces and in public spaces 49 | when an individual is representing the project or its community. Examples of 50 | representing a project or community include using an official project e-mail 51 | address, posting via an official social media account, or acting as an appointed 52 | representative at an online or offline event. Representation of a project may be 53 | further defined and clarified by project maintainers. 54 | 55 | ## Enforcement 56 | 57 | Instances of abusive, harassing, or otherwise unacceptable behavior may be 58 | reported by contacting the project team at imfunny@wybemf.com. All 59 | complaints will be reviewed and investigated and will result in a response that 60 | is deemed necessary and appropriate to the circumstances. The project team is 61 | obligated to maintain confidentiality with regard to the reporter of an incident. 62 | Further details of specific enforcement policies may be posted separately. 63 | 64 | Project maintainers who do not follow or enforce the Code of Conduct in good 65 | faith may face temporary or permanent repercussions as determined by other 66 | members of the project's leadership. 67 | 68 | ## Attribution 69 | 70 | This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4, 71 | available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html 72 | 73 | [homepage]: https://www.contributor-covenant.org 74 | 75 | For answers to common questions about this code of conduct, see 76 | https://www.contributor-covenant.org/faq 77 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | Preamble 9 | 10 | The GNU General Public License is a free, copyleft license for 11 | software and other kinds of works. 12 | 13 | The licenses for most software and other practical works are designed 14 | to take away your freedom to share and change the works. By contrast, 15 | the GNU General Public License is intended to guarantee your freedom to 16 | share and change all versions of a program--to make sure it remains free 17 | software for all its users. We, the Free Software Foundation, use the 18 | GNU General Public License for most of our software; it applies also to 19 | any other work released this way by its authors. You can apply it to 20 | your programs, too. 21 | 22 | When we speak of free software, we are referring to freedom, not 23 | price. Our General Public Licenses are designed to make sure that you 24 | have the freedom to distribute copies of free software (and charge for 25 | them if you wish), that you receive source code or can get it if you 26 | want it, that you can change the software or use pieces of it in new 27 | free programs, and that you know you can do these things. 28 | 29 | To protect your rights, we need to prevent others from denying you 30 | these rights or asking you to surrender the rights. Therefore, you have 31 | certain responsibilities if you distribute copies of the software, or if 32 | you modify it: responsibilities to respect the freedom of others. 33 | 34 | For example, if you distribute copies of such a program, whether 35 | gratis or for a fee, you must pass on to the recipients the same 36 | freedoms that you received. You must make sure that they, too, receive 37 | or can get the source code. And you must show them these terms so they 38 | know their rights. 39 | 40 | Developers that use the GNU GPL protect your rights with two steps: 41 | (1) assert copyright on the software, and (2) offer you this License 42 | giving you legal permission to copy, distribute and/or modify it. 43 | 44 | For the developers' and authors' protection, the GPL clearly explains 45 | that there is no warranty for this free software. For both users' and 46 | authors' sake, the GPL requires that modified versions be marked as 47 | changed, so that their problems will not be attributed erroneously to 48 | authors of previous versions. 49 | 50 | Some devices are designed to deny users access to install or run 51 | modified versions of the software inside them, although the manufacturer 52 | can do so. This is fundamentally incompatible with the aim of 53 | protecting users' freedom to change the software. The systematic 54 | pattern of such abuse occurs in the area of products for individuals to 55 | use, which is precisely where it is most unacceptable. Therefore, we 56 | have designed this version of the GPL to prohibit the practice for those 57 | products. If such problems arise substantially in other domains, we 58 | stand ready to extend this provision to those domains in future versions 59 | of the GPL, as needed to protect the freedom of users. 60 | 61 | Finally, every program is threatened constantly by software patents. 62 | States should not allow patents to restrict development and use of 63 | software on general-purpose computers, but in those that do, we wish to 64 | avoid the special danger that patents applied to a free program could 65 | make it effectively proprietary. To prevent this, the GPL assures that 66 | patents cannot be used to render the program non-free. 67 | 68 | The precise terms and conditions for copying, distribution and 69 | modification follow. 70 | 71 | TERMS AND CONDITIONS 72 | 73 | 0. Definitions. 74 | 75 | "This License" refers to version 3 of the GNU General Public License. 76 | 77 | "Copyright" also means copyright-like laws that apply to other kinds of 78 | works, such as semiconductor masks. 79 | 80 | "The Program" refers to any copyrightable work licensed under this 81 | License. Each licensee is addressed as "you". "Licensees" and 82 | "recipients" may be individuals or organizations. 83 | 84 | To "modify" a work means to copy from or adapt all or part of the work 85 | in a fashion requiring copyright permission, other than the making of an 86 | exact copy. The resulting work is called a "modified version" of the 87 | earlier work or a work "based on" the earlier work. 88 | 89 | A "covered work" means either the unmodified Program or a work based 90 | on the Program. 91 | 92 | To "propagate" a work means to do anything with it that, without 93 | permission, would make you directly or secondarily liable for 94 | infringement under applicable copyright law, except executing it on a 95 | computer or modifying a private copy. Propagation includes copying, 96 | distribution (with or without modification), making available to the 97 | public, and in some countries other activities as well. 98 | 99 | To "convey" a work means any kind of propagation that enables other 100 | parties to make or receive copies. Mere interaction with a user through 101 | a computer network, with no transfer of a copy, is not conveying. 102 | 103 | An interactive user interface displays "Appropriate Legal Notices" 104 | to the extent that it includes a convenient and prominently visible 105 | feature that (1) displays an appropriate copyright notice, and (2) 106 | tells the user that there is no warranty for the work (except to the 107 | extent that warranties are provided), that licensees may convey the 108 | work under this License, and how to view a copy of this License. If 109 | the interface presents a list of user commands or options, such as a 110 | menu, a prominent item in the list meets this criterion. 111 | 112 | 1. Source Code. 113 | 114 | The "source code" for a work means the preferred form of the work 115 | for making modifications to it. "Object code" means any non-source 116 | form of a work. 117 | 118 | A "Standard Interface" means an interface that either is an official 119 | standard defined by a recognized standards body, or, in the case of 120 | interfaces specified for a particular programming language, one that 121 | is widely used among developers working in that language. 122 | 123 | The "System Libraries" of an executable work include anything, other 124 | than the work as a whole, that (a) is included in the normal form of 125 | packaging a Major Component, but which is not part of that Major 126 | Component, and (b) serves only to enable use of the work with that 127 | Major Component, or to implement a Standard Interface for which an 128 | implementation is available to the public in source code form. A 129 | "Major Component", in this context, means a major essential component 130 | (kernel, window system, and so on) of the specific operating system 131 | (if any) on which the executable work runs, or a compiler used to 132 | produce the work, or an object code interpreter used to run it. 133 | 134 | The "Corresponding Source" for a work in object code form means all 135 | the source code needed to generate, install, and (for an executable 136 | work) run the object code and to modify the work, including scripts to 137 | control those activities. However, it does not include the work's 138 | System Libraries, or general-purpose tools or generally available free 139 | programs which are used unmodified in performing those activities but 140 | which are not part of the work. For example, Corresponding Source 141 | includes interface definition files associated with source files for 142 | the work, and the source code for shared libraries and dynamically 143 | linked subprograms that the work is specifically designed to require, 144 | such as by intimate data communication or control flow between those 145 | subprograms and other parts of the work. 146 | 147 | The Corresponding Source need not include anything that users 148 | can regenerate automatically from other parts of the Corresponding 149 | Source. 150 | 151 | The Corresponding Source for a work in source code form is that 152 | same work. 153 | 154 | 2. Basic Permissions. 155 | 156 | All rights granted under this License are granted for the term of 157 | copyright on the Program, and are irrevocable provided the stated 158 | conditions are met. This License explicitly affirms your unlimited 159 | permission to run the unmodified Program. The output from running a 160 | covered work is covered by this License only if the output, given its 161 | content, constitutes a covered work. This License acknowledges your 162 | rights of fair use or other equivalent, as provided by copyright law. 163 | 164 | You may make, run and propagate covered works that you do not 165 | convey, without conditions so long as your license otherwise remains 166 | in force. You may convey covered works to others for the sole purpose 167 | of having them make modifications exclusively for you, or provide you 168 | with facilities for running those works, provided that you comply with 169 | the terms of this License in conveying all material for which you do 170 | not control copyright. Those thus making or running the covered works 171 | for you must do so exclusively on your behalf, under your direction 172 | and control, on terms that prohibit them from making any copies of 173 | your copyrighted material outside their relationship with you. 174 | 175 | Conveying under any other circumstances is permitted solely under 176 | the conditions stated below. Sublicensing is not allowed; section 10 177 | makes it unnecessary. 178 | 179 | 3. Protecting Users' Legal Rights From Anti-Circumvention Law. 180 | 181 | No covered work shall be deemed part of an effective technological 182 | measure under any applicable law fulfilling obligations under article 183 | 11 of the WIPO copyright treaty adopted on 20 December 1996, or 184 | similar laws prohibiting or restricting circumvention of such 185 | measures. 186 | 187 | When you convey a covered work, you waive any legal power to forbid 188 | circumvention of technological measures to the extent such circumvention 189 | is effected by exercising rights under this License with respect to 190 | the covered work, and you disclaim any intention to limit operation or 191 | modification of the work as a means of enforcing, against the work's 192 | users, your or third parties' legal rights to forbid circumvention of 193 | technological measures. 194 | 195 | 4. Conveying Verbatim Copies. 196 | 197 | You may convey verbatim copies of the Program's source code as you 198 | receive it, in any medium, provided that you conspicuously and 199 | appropriately publish on each copy an appropriate copyright notice; 200 | keep intact all notices stating that this License and any 201 | non-permissive terms added in accord with section 7 apply to the code; 202 | keep intact all notices of the absence of any warranty; and give all 203 | recipients a copy of this License along with the Program. 204 | 205 | You may charge any price or no price for each copy that you convey, 206 | and you may offer support or warranty protection for a fee. 207 | 208 | 5. Conveying Modified Source Versions. 209 | 210 | You may convey a work based on the Program, or the modifications to 211 | produce it from the Program, in the form of source code under the 212 | terms of section 4, provided that you also meet all of these conditions: 213 | 214 | a) The work must carry prominent notices stating that you modified 215 | it, and giving a relevant date. 216 | 217 | b) The work must carry prominent notices stating that it is 218 | released under this License and any conditions added under section 219 | 7. This requirement modifies the requirement in section 4 to 220 | "keep intact all notices". 221 | 222 | c) You must license the entire work, as a whole, under this 223 | License to anyone who comes into possession of a copy. This 224 | License will therefore apply, along with any applicable section 7 225 | additional terms, to the whole of the work, and all its parts, 226 | regardless of how they are packaged. This License gives no 227 | permission to license the work in any other way, but it does not 228 | invalidate such permission if you have separately received it. 229 | 230 | d) If the work has interactive user interfaces, each must display 231 | Appropriate Legal Notices; however, if the Program has interactive 232 | interfaces that do not display Appropriate Legal Notices, your 233 | work need not make them do so. 234 | 235 | A compilation of a covered work with other separate and independent 236 | works, which are not by their nature extensions of the covered work, 237 | and which are not combined with it such as to form a larger program, 238 | in or on a volume of a storage or distribution medium, is called an 239 | "aggregate" if the compilation and its resulting copyright are not 240 | used to limit the access or legal rights of the compilation's users 241 | beyond what the individual works permit. Inclusion of a covered work 242 | in an aggregate does not cause this License to apply to the other 243 | parts of the aggregate. 244 | 245 | 6. Conveying Non-Source Forms. 246 | 247 | You may convey a covered work in object code form under the terms 248 | of sections 4 and 5, provided that you also convey the 249 | machine-readable Corresponding Source under the terms of this License, 250 | in one of these ways: 251 | 252 | a) Convey the object code in, or embodied in, a physical product 253 | (including a physical distribution medium), accompanied by the 254 | Corresponding Source fixed on a durable physical medium 255 | customarily used for software interchange. 256 | 257 | b) Convey the object code in, or embodied in, a physical product 258 | (including a physical distribution medium), accompanied by a 259 | written offer, valid for at least three years and valid for as 260 | long as you offer spare parts or customer support for that product 261 | model, to give anyone who possesses the object code either (1) a 262 | copy of the Corresponding Source for all the software in the 263 | product that is covered by this License, on a durable physical 264 | medium customarily used for software interchange, for a price no 265 | more than your reasonable cost of physically performing this 266 | conveying of source, or (2) access to copy the 267 | Corresponding Source from a network server at no charge. 268 | 269 | c) Convey individual copies of the object code with a copy of the 270 | written offer to provide the Corresponding Source. This 271 | alternative is allowed only occasionally and noncommercially, and 272 | only if you received the object code with such an offer, in accord 273 | with subsection 6b. 274 | 275 | d) Convey the object code by offering access from a designated 276 | place (gratis or for a charge), and offer equivalent access to the 277 | Corresponding Source in the same way through the same place at no 278 | further charge. You need not require recipients to copy the 279 | Corresponding Source along with the object code. If the place to 280 | copy the object code is a network server, the Corresponding Source 281 | may be on a different server (operated by you or a third party) 282 | that supports equivalent copying facilities, provided you maintain 283 | clear directions next to the object code saying where to find the 284 | Corresponding Source. Regardless of what server hosts the 285 | Corresponding Source, you remain obligated to ensure that it is 286 | available for as long as needed to satisfy these requirements. 287 | 288 | e) Convey the object code using peer-to-peer transmission, provided 289 | you inform other peers where the object code and Corresponding 290 | Source of the work are being offered to the general public at no 291 | charge under subsection 6d. 292 | 293 | A separable portion of the object code, whose source code is excluded 294 | from the Corresponding Source as a System Library, need not be 295 | included in conveying the object code work. 296 | 297 | A "User Product" is either (1) a "consumer product", which means any 298 | tangible personal property which is normally used for personal, family, 299 | or household purposes, or (2) anything designed or sold for incorporation 300 | into a dwelling. In determining whether a product is a consumer product, 301 | doubtful cases shall be resolved in favor of coverage. For a particular 302 | product received by a particular user, "normally used" refers to a 303 | typical or common use of that class of product, regardless of the status 304 | of the particular user or of the way in which the particular user 305 | actually uses, or expects or is expected to use, the product. A product 306 | is a consumer product regardless of whether the product has substantial 307 | commercial, industrial or non-consumer uses, unless such uses represent 308 | the only significant mode of use of the product. 309 | 310 | "Installation Information" for a User Product means any methods, 311 | procedures, authorization keys, or other information required to install 312 | and execute modified versions of a covered work in that User Product from 313 | a modified version of its Corresponding Source. The information must 314 | suffice to ensure that the continued functioning of the modified object 315 | code is in no case prevented or interfered with solely because 316 | modification has been made. 317 | 318 | If you convey an object code work under this section in, or with, or 319 | specifically for use in, a User Product, and the conveying occurs as 320 | part of a transaction in which the right of possession and use of the 321 | User Product is transferred to the recipient in perpetuity or for a 322 | fixed term (regardless of how the transaction is characterized), the 323 | Corresponding Source conveyed under this section must be accompanied 324 | by the Installation Information. But this requirement does not apply 325 | if neither you nor any third party retains the ability to install 326 | modified object code on the User Product (for example, the work has 327 | been installed in ROM). 328 | 329 | The requirement to provide Installation Information does not include a 330 | requirement to continue to provide support service, warranty, or updates 331 | for a work that has been modified or installed by the recipient, or for 332 | the User Product in which it has been modified or installed. Access to a 333 | network may be denied when the modification itself materially and 334 | adversely affects the operation of the network or violates the rules and 335 | protocols for communication across the network. 336 | 337 | Corresponding Source conveyed, and Installation Information provided, 338 | in accord with this section must be in a format that is publicly 339 | documented (and with an implementation available to the public in 340 | source code form), and must require no special password or key for 341 | unpacking, reading or copying. 342 | 343 | 7. Additional Terms. 344 | 345 | "Additional permissions" are terms that supplement the terms of this 346 | License by making exceptions from one or more of its conditions. 347 | Additional permissions that are applicable to the entire Program shall 348 | be treated as though they were included in this License, to the extent 349 | that they are valid under applicable law. If additional permissions 350 | apply only to part of the Program, that part may be used separately 351 | under those permissions, but the entire Program remains governed by 352 | this License without regard to the additional permissions. 353 | 354 | When you convey a copy of a covered work, you may at your option 355 | remove any additional permissions from that copy, or from any part of 356 | it. (Additional permissions may be written to require their own 357 | removal in certain cases when you modify the work.) You may place 358 | additional permissions on material, added by you to a covered work, 359 | for which you have or can give appropriate copyright permission. 360 | 361 | Notwithstanding any other provision of this License, for material you 362 | add to a covered work, you may (if authorized by the copyright holders of 363 | that material) supplement the terms of this License with terms: 364 | 365 | a) Disclaiming warranty or limiting liability differently from the 366 | terms of sections 15 and 16 of this License; or 367 | 368 | b) Requiring preservation of specified reasonable legal notices or 369 | author attributions in that material or in the Appropriate Legal 370 | Notices displayed by works containing it; or 371 | 372 | c) Prohibiting misrepresentation of the origin of that material, or 373 | requiring that modified versions of such material be marked in 374 | reasonable ways as different from the original version; or 375 | 376 | d) Limiting the use for publicity purposes of names of licensors or 377 | authors of the material; or 378 | 379 | e) Declining to grant rights under trademark law for use of some 380 | trade names, trademarks, or service marks; or 381 | 382 | f) Requiring indemnification of licensors and authors of that 383 | material by anyone who conveys the material (or modified versions of 384 | it) with contractual assumptions of liability to the recipient, for 385 | any liability that these contractual assumptions directly impose on 386 | those licensors and authors. 387 | 388 | All other non-permissive additional terms are considered "further 389 | restrictions" within the meaning of section 10. If the Program as you 390 | received it, or any part of it, contains a notice stating that it is 391 | governed by this License along with a term that is a further 392 | restriction, you may remove that term. If a license document contains 393 | a further restriction but permits relicensing or conveying under this 394 | License, you may add to a covered work material governed by the terms 395 | of that license document, provided that the further restriction does 396 | not survive such relicensing or conveying. 397 | 398 | If you add terms to a covered work in accord with this section, you 399 | must place, in the relevant source files, a statement of the 400 | additional terms that apply to those files, or a notice indicating 401 | where to find the applicable terms. 402 | 403 | Additional terms, permissive or non-permissive, may be stated in the 404 | form of a separately written license, or stated as exceptions; 405 | the above requirements apply either way. 406 | 407 | 8. Termination. 408 | 409 | You may not propagate or modify a covered work except as expressly 410 | provided under this License. Any attempt otherwise to propagate or 411 | modify it is void, and will automatically terminate your rights under 412 | this License (including any patent licenses granted under the third 413 | paragraph of section 11). 414 | 415 | However, if you cease all violation of this License, then your 416 | license from a particular copyright holder is reinstated (a) 417 | provisionally, unless and until the copyright holder explicitly and 418 | finally terminates your license, and (b) permanently, if the copyright 419 | holder fails to notify you of the violation by some reasonable means 420 | prior to 60 days after the cessation. 421 | 422 | Moreover, your license from a particular copyright holder is 423 | reinstated permanently if the copyright holder notifies you of the 424 | violation by some reasonable means, this is the first time you have 425 | received notice of violation of this License (for any work) from that 426 | copyright holder, and you cure the violation prior to 30 days after 427 | your receipt of the notice. 428 | 429 | Termination of your rights under this section does not terminate the 430 | licenses of parties who have received copies or rights from you under 431 | this License. If your rights have been terminated and not permanently 432 | reinstated, you do not qualify to receive new licenses for the same 433 | material under section 10. 434 | 435 | 9. Acceptance Not Required for Having Copies. 436 | 437 | You are not required to accept this License in order to receive or 438 | run a copy of the Program. Ancillary propagation of a covered work 439 | occurring solely as a consequence of using peer-to-peer transmission 440 | to receive a copy likewise does not require acceptance. However, 441 | nothing other than this License grants you permission to propagate or 442 | modify any covered work. These actions infringe copyright if you do 443 | not accept this License. Therefore, by modifying or propagating a 444 | covered work, you indicate your acceptance of this License to do so. 445 | 446 | 10. Automatic Licensing of Downstream Recipients. 447 | 448 | Each time you convey a covered work, the recipient automatically 449 | receives a license from the original licensors, to run, modify and 450 | propagate that work, subject to this License. You are not responsible 451 | for enforcing compliance by third parties with this License. 452 | 453 | An "entity transaction" is a transaction transferring control of an 454 | organization, or substantially all assets of one, or subdividing an 455 | organization, or merging organizations. If propagation of a covered 456 | work results from an entity transaction, each party to that 457 | transaction who receives a copy of the work also receives whatever 458 | licenses to the work the party's predecessor in interest had or could 459 | give under the previous paragraph, plus a right to possession of the 460 | Corresponding Source of the work from the predecessor in interest, if 461 | the predecessor has it or can get it with reasonable efforts. 462 | 463 | You may not impose any further restrictions on the exercise of the 464 | rights granted or affirmed under this License. For example, you may 465 | not impose a license fee, royalty, or other charge for exercise of 466 | rights granted under this License, and you may not initiate litigation 467 | (including a cross-claim or counterclaim in a lawsuit) alleging that 468 | any patent claim is infringed by making, using, selling, offering for 469 | sale, or importing the Program or any portion of it. 470 | 471 | 11. Patents. 472 | 473 | A "contributor" is a copyright holder who authorizes use under this 474 | License of the Program or a work on which the Program is based. The 475 | work thus licensed is called the contributor's "contributor version". 476 | 477 | A contributor's "essential patent claims" are all patent claims 478 | owned or controlled by the contributor, whether already acquired or 479 | hereafter acquired, that would be infringed by some manner, permitted 480 | by this License, of making, using, or selling its contributor version, 481 | but do not include claims that would be infringed only as a 482 | consequence of further modification of the contributor version. For 483 | purposes of this definition, "control" includes the right to grant 484 | patent sublicenses in a manner consistent with the requirements of 485 | this License. 486 | 487 | Each contributor grants you a non-exclusive, worldwide, royalty-free 488 | patent license under the contributor's essential patent claims, to 489 | make, use, sell, offer for sale, import and otherwise run, modify and 490 | propagate the contents of its contributor version. 491 | 492 | In the following three paragraphs, a "patent license" is any express 493 | agreement or commitment, however denominated, not to enforce a patent 494 | (such as an express permission to practice a patent or covenant not to 495 | sue for patent infringement). To "grant" such a patent license to a 496 | party means to make such an agreement or commitment not to enforce a 497 | patent against the party. 498 | 499 | If you convey a covered work, knowingly relying on a patent license, 500 | and the Corresponding Source of the work is not available for anyone 501 | to copy, free of charge and under the terms of this License, through a 502 | publicly available network server or other readily accessible means, 503 | then you must either (1) cause the Corresponding Source to be so 504 | available, or (2) arrange to deprive yourself of the benefit of the 505 | patent license for this particular work, or (3) arrange, in a manner 506 | consistent with the requirements of this License, to extend the patent 507 | license to downstream recipients. "Knowingly relying" means you have 508 | actual knowledge that, but for the patent license, your conveying the 509 | covered work in a country, or your recipient's use of the covered work 510 | in a country, would infringe one or more identifiable patents in that 511 | country that you have reason to believe are valid. 512 | 513 | If, pursuant to or in connection with a single transaction or 514 | arrangement, you convey, or propagate by procuring conveyance of, a 515 | covered work, and grant a patent license to some of the parties 516 | receiving the covered work authorizing them to use, propagate, modify 517 | or convey a specific copy of the covered work, then the patent license 518 | you grant is automatically extended to all recipients of the covered 519 | work and works based on it. 520 | 521 | A patent license is "discriminatory" if it does not include within 522 | the scope of its coverage, prohibits the exercise of, or is 523 | conditioned on the non-exercise of one or more of the rights that are 524 | specifically granted under this License. You may not convey a covered 525 | work if you are a party to an arrangement with a third party that is 526 | in the business of distributing software, under which you make payment 527 | to the third party based on the extent of your activity of conveying 528 | the work, and under which the third party grants, to any of the 529 | parties who would receive the covered work from you, a discriminatory 530 | patent license (a) in connection with copies of the covered work 531 | conveyed by you (or copies made from those copies), or (b) primarily 532 | for and in connection with specific products or compilations that 533 | contain the covered work, unless you entered into that arrangement, 534 | or that patent license was granted, prior to 28 March 2007. 535 | 536 | Nothing in this License shall be construed as excluding or limiting 537 | any implied license or other defenses to infringement that may 538 | otherwise be available to you under applicable patent law. 539 | 540 | 12. No Surrender of Others' Freedom. 541 | 542 | If conditions are imposed on you (whether by court order, agreement or 543 | otherwise) that contradict the conditions of this License, they do not 544 | excuse you from the conditions of this License. If you cannot convey a 545 | covered work so as to satisfy simultaneously your obligations under this 546 | License and any other pertinent obligations, then as a consequence you may 547 | not convey it at all. For example, if you agree to terms that obligate you 548 | to collect a royalty for further conveying from those to whom you convey 549 | the Program, the only way you could satisfy both those terms and this 550 | License would be to refrain entirely from conveying the Program. 551 | 552 | 13. Use with the GNU Affero General Public License. 553 | 554 | Notwithstanding any other provision of this License, you have 555 | permission to link or combine any covered work with a work licensed 556 | under version 3 of the GNU Affero General Public License into a single 557 | combined work, and to convey the resulting work. The terms of this 558 | License will continue to apply to the part which is the covered work, 559 | but the special requirements of the GNU Affero General Public License, 560 | section 13, concerning interaction through a network will apply to the 561 | combination as such. 562 | 563 | 14. Revised Versions of this License. 564 | 565 | The Free Software Foundation may publish revised and/or new versions of 566 | the GNU General Public License from time to time. Such new versions will 567 | be similar in spirit to the present version, but may differ in detail to 568 | address new problems or concerns. 569 | 570 | Each version is given a distinguishing version number. If the 571 | Program specifies that a certain numbered version of the GNU General 572 | Public License "or any later version" applies to it, you have the 573 | option of following the terms and conditions either of that numbered 574 | version or of any later version published by the Free Software 575 | Foundation. If the Program does not specify a version number of the 576 | GNU General Public License, you may choose any version ever published 577 | by the Free Software Foundation. 578 | 579 | If the Program specifies that a proxy can decide which future 580 | versions of the GNU General Public License can be used, that proxy's 581 | public statement of acceptance of a version permanently authorizes you 582 | to choose that version for the Program. 583 | 584 | Later license versions may give you additional or different 585 | permissions. However, no additional obligations are imposed on any 586 | author or copyright holder as a result of your choosing to follow a 587 | later version. 588 | 589 | 15. Disclaimer of Warranty. 590 | 591 | THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY 592 | APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT 593 | HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY 594 | OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, 595 | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 596 | PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM 597 | IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF 598 | ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 599 | 600 | 16. Limitation of Liability. 601 | 602 | IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING 603 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS 604 | THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY 605 | GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE 606 | USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF 607 | DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD 608 | PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), 609 | EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF 610 | SUCH DAMAGES. 611 | 612 | 17. Interpretation of Sections 15 and 16. 613 | 614 | If the disclaimer of warranty and limitation of liability provided 615 | above cannot be given local legal effect according to their terms, 616 | reviewing courts shall apply local law that most closely approximates 617 | an absolute waiver of all civil liability in connection with the 618 | Program, unless a warranty or assumption of liability accompanies a 619 | copy of the Program in return for a fee. 620 | 621 | END OF TERMS AND CONDITIONS 622 | 623 | How to Apply These Terms to Your New Programs 624 | 625 | If you develop a new program, and you want it to be of the greatest 626 | possible use to the public, the best way to achieve this is to make it 627 | free software which everyone can redistribute and change under these terms. 628 | 629 | To do so, attach the following notices to the program. It is safest 630 | to attach them to the start of each source file to most effectively 631 | state the exclusion of warranty; and each file should have at least 632 | the "copyright" line and a pointer to where the full notice is found. 633 | 634 | 635 | Copyright (C) 636 | 637 | This program is free software: you can redistribute it and/or modify 638 | it under the terms of the GNU General Public License as published by 639 | the Free Software Foundation, either version 3 of the License, or 640 | (at your option) any later version. 641 | 642 | This program is distributed in the hope that it will be useful, 643 | but WITHOUT ANY WARRANTY; without even the implied warranty of 644 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 645 | GNU General Public License for more details. 646 | 647 | You should have received a copy of the GNU General Public License 648 | along with this program. If not, see . 649 | 650 | Also add information on how to contact you by electronic and paper mail. 651 | 652 | If the program does terminal interaction, make it output a short 653 | notice like this when it starts in an interactive mode: 654 | 655 | Copyright (C) 656 | This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'. 657 | This is free software, and you are welcome to redistribute it 658 | under certain conditions; type `show c' for details. 659 | 660 | The hypothetical commands `show w' and `show c' should show the appropriate 661 | parts of the General Public License. Of course, your program's commands 662 | might be different; for a GUI interface, you would use an "about box". 663 | 664 | You should also get your employer (if you work as a programmer) or school, 665 | if any, to sign a "copyright disclaimer" for the program, if necessary. 666 | For more information on this, and how to apply and follow the GNU GPL, see 667 | . 668 | 669 | The GNU General Public License does not permit incorporating your program 670 | into proprietary programs. If your program is a subroutine library, you 671 | may consider it more useful to permit linking proprietary applications with 672 | the library. If this is what you want to do, use the GNU Lesser General 673 | Public License instead of this License. But first, please read 674 | . 675 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ### archived in favor of v2 release soon ;) 2 | 3 | 4 | 5 | # Gitfolio 6 | [![Tweet](https://img.shields.io/twitter/url/https/shields.io.svg?style=social)](https://twitter.com/intent/tweet?text=personal%20website%20and%20a%20blog%20for%20every%20github%20user%20@imfunnieee%20&url=https://github.com/imfunniee/gitfolio) ![GitHub release](https://img.shields.io/github/release/imfunniee/gitfolio.svg?style=popout-square) ![npm](https://img.shields.io/npm/dm/gitfolio.svg?style=popout-square) ![GitHub top language](https://img.shields.io/github/languages/top/imfunniee/gitfolio.svg?style=popout-square) ![GitHub last commit](https://img.shields.io/github/last-commit/imfunniee/gitfolio.svg?style=popout-square) ![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square) [![code style: prettier](https://img.shields.io/badge/code_style-prettier-ff69b4.svg?style=flat-square)](https://github.com/prettier/prettier) 7 | 8 | ### personal website + blog for every github user 9 | 10 | Gitfolio will help you get started with a portfolio website where you could showcase your work + a blog that will help you spread your ideas into real world. 11 | 12 | Check out this [live demo](https://imfunniee.github.io/gitfolio/) to see gitfolio in action. 13 | 14 | # Getting Started 15 | 16 | ### Let's Install 17 | 18 | Install gitfolio 19 | 20 | ```sh 21 | npm i gitfolio -g 22 | ``` 23 | 24 | ### Let's Build 25 | 26 | Using the UI 27 | 28 | ```sh 29 | $ gitfolio ui 30 | ``` 31 | 32 | > Tip: You can use ui to create new blogs and for updating your folio too. 33 | 34 | or 35 | 36 | ```sh 37 | gitfolio build 38 | ``` 39 | 40 | `` is your username on github. This will build your website using your GitHub username and put it in the `/dist` folder. 41 | 42 | To run your website use `run` command, Default port is 3000 43 | 44 | ```sh 45 | gitfolio run -p [port] 46 | ``` 47 | 48 | 🎉 Congrats, you just made yourself a personal website! 49 | 50 | ### Let's Customize 51 | 52 | #### Forks 53 | 54 | To include forks on your personal website just provide `-f` or `--fork` argument while building 55 | 56 | ```sh 57 | $ gitfolio build -f 58 | ``` 59 | 60 | #### Sorting Repos 61 | 62 | To sort repos provide `--sort [sortBy]` argument while building. Where `[sortBy]` can be `star`, `created`, `updated`, `pushed`,`full_name`. Default: `created` 63 | 64 | ```sh 65 | $ gitfolio build --sort star 66 | ``` 67 | 68 | #### Ordering Repos 69 | 70 | To order the sorted repos provide `--order [orderBy]` argument while building. Where `[orderBy]` can be `asc` or `desc`. Default: `asc` 71 | 72 | ```sh 73 | $ gitfolio build --sort star --order desc 74 | ``` 75 | 76 | #### Customize Themes 77 | 78 | Themes are specified using the `--theme [theme-name]` flag when running the `build` command. The available themes are 79 | 80 | - `light` 81 | - `dark` 82 | 83 | > TODO: Add more themes 84 | 85 | For example, the following command will build the website with the dark theme 86 | 87 | ```sh 88 | $ gitfolio build --theme dark 89 | ``` 90 | 91 | #### Customize background image 92 | 93 | To customize the background image just provide `--background [url]` argument while building 94 | 95 | ```sh 96 | $ gitfolio build --background https://images.unsplash.com/photo-1557277770-baf0ca74f908?w=1634 97 | ``` 98 | 99 | You could also add in your custom CSS inside `index.css` to give it a more personal feel. 100 | 101 | #### Add Social Media links on your profile 102 | 103 | Twitter, LinkedIn, Medium & Dribbble links to your profile while building 104 | 105 | ```sh 106 | gitfolio build --twitter --linkedin --medium --dribbble 107 | ``` 108 | 109 | ### Let's Publish 110 | 111 | Head over to GitHub and create a new repository named `username.github.io`, where username is your username. Push the files inside`/dist` folder to repo you just created. 112 | 113 | Go To `username.github.io` your site should be up!! 114 | 115 | ### Updating 116 | 117 | To update your info, simply run 118 | 119 | ```sh 120 | $ gitfolio update 121 | ``` 122 | 123 | or use the `Update` options in gitfolio's UI 124 | 125 | This will update your info and your repository info. 126 | 127 | To Update background or theme you need to run `build` command again. 128 | 129 | ### Add a Blog 130 | 131 | To add your first blog use the UI. 132 | 133 | ```sh 134 | $ gitfolio ui 135 | ``` 136 | 137 | This will open up a UI page and you can click on `New Blog` to create a new blog. Once you are done writing your blog you can hit the `Create Blog`. 138 | 139 | This will create a blog inside `./dist/blog` folder. 140 | 141 | Look for success or error in your terminal. 142 | 143 | This also adds content to `blog.json` file. This file helps in showcasing your blogs on your personal website as [cards](https://imfunniee.github.io/gitfolio/#blog_section). You could customize the JSON object that corresponds your current blog. 144 | 145 | Blog Demo? [here](https://imfunniee.github.io/gitfolio/blog/my-first-post/) 146 | 147 | Blog's default JSON Format 148 | 149 | ``` 150 | { 151 | "url_title": "my-first-blog", // the title you provide while creating a new blog, this appears in url 152 | "title": "Lorem ipsum dolor sit amet", // main title of blog 153 | "sub_title": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", // sub-title of blog 154 | "top_image": "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1450", // main image of blog 155 | "visible": true // don't worry about this 156 | } 157 | ``` 158 | 159 | ### Follow me on twitter for more updates [@imfunnieee](https://twitter.com/imfunnieee) 160 | 161 | ### License 162 | 163 | ![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square) 164 | -------------------------------------------------------------------------------- /api.js: -------------------------------------------------------------------------------- 1 | const got = require("got"); 2 | 3 | /** 4 | * The defaults here are the same as the API 5 | * @see https://developer.github.com/v3/repos/#list-user-repositories 6 | * @param {string} username 7 | * @param {Object} opts 8 | * @param {('all' | 'owner' | 'member')[]} [opts.types] 9 | * @param {'created' | 'updated' | 'pushed' | 'full_name' | 'star'} [opts.sort] 10 | * @param {'desc' | 'asc'} [opts.order] 11 | */ 12 | async function getRepos(username, opts = {}) { 13 | let tempRepos; 14 | let page = 1; 15 | let repos = []; 16 | 17 | const sort = opts.sort; 18 | const order = opts.order || (sort === "full_name" ? "asc" : "desc"); 19 | const types = opts.types || []; 20 | let type = "all"; 21 | 22 | if ( 23 | types.includes("all") || 24 | (types.includes("owner") && types.includes("member")) 25 | ) { 26 | type = "all"; 27 | } else if (types.includes("member")) { 28 | type = "member"; 29 | } 30 | 31 | do { 32 | let requestUrl = `https://api.github.com/users/${username}/repos?per_page=100&page=${page++}&type=${type}`; 33 | if (sort && sort !== "star") { 34 | requestUrl += `&sort=${sort}&direction=${order}`; 35 | } 36 | tempRepos = await got(requestUrl); 37 | tempRepos = JSON.parse(tempRepos.body); 38 | repos = repos.concat(tempRepos); 39 | } while (tempRepos.length == 100); 40 | 41 | if (sort == "star") { 42 | repos = repos.sort(function(a, b) { 43 | if (order == "desc") { 44 | return b.stargazers_count - a.stargazers_count; 45 | } else { 46 | return a.stargazers_count - b.stargazers_count; 47 | } 48 | }); 49 | } 50 | 51 | return repos; 52 | } 53 | 54 | /** 55 | * @see https://developer.github.com/v3/users/#get-a-single-user 56 | * @param {string} username 57 | */ 58 | async function getUser(username) { 59 | const res = await got(`https://api.github.com/users/${username}`); 60 | return JSON.parse(res.body); 61 | } 62 | 63 | module.exports = { 64 | getRepos, 65 | getUser 66 | }; 67 | -------------------------------------------------------------------------------- /assets/blog/blog.json: -------------------------------------------------------------------------------- 1 | [] 2 | -------------------------------------------------------------------------------- /assets/blog/blogTemplate.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Lorem ipsum dolor 8 | 12 | 18 | 23 | 24 | 25 |
26 |
27 |
28 | 29 |
30 |
31 | 32 | 33 | 34 | 35 | 38 | 39 | 40 |
36 |
37 |
41 |
42 |

Lorem ipsum dolor

43 |

44 | Lorem ipsum dolor sit amet, consectetur adipiscing elit. 45 |

46 |
47 | 50 |

51 | Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut placerat 52 | pretium sem, ac maximus dui sodales a. Nunc aliquet hendrerit turpis 53 | ac egestas. Phasellus volutpat tristique maximus. 54 | Pellentesque feugiat eget nisi et dignissim. Nam nibh erat, 55 | sollicitudin non facilisis nec, scelerisque nec ipsum. Sed accumsan 56 | velit condimentum, pharetra felis vitae, commodo tellus. 57 | Mauris consequat luctus orci. 58 |

59 |

60 | Vivamus pharetra lobortis dui non tincidunt. Mauris vitae nisi 61 | vestibulum, mollis magna a, maximus mi. Suspendisse dictum eget augue 62 | quis sodales. Quisque rutrum ligula nec dapibus tincidunt. 63 | Proin hendrerit massa a tellus vestibulum, a hendrerit ipsum 65 | iaculis. Suspendisse potenti. 67 | Praesent eget erat blandit, finibus sapien vitae, ullamcorper erat. 68 | Integer blandit, felis at ullamcorper maximus, odio lectus pretium 69 | mauris, vel consequat lectus quam eu risus. Pellentesque gravida nec 70 | diam eget vehicula. 71 |

72 | 75 |

76 | Donec hendrerit turpis non libero eleifend dignissim. Mauris non 77 | tempor metus, et tristique massa. Integer consequat justo quam, vitae 78 | aliquam arcu vestibulum at. Donec porttitor quam in tempus convallis. 79 | Praesent feugiat eget eros vitae accumsan. Duis ultricies odio quis 80 | nisl volutpat, consectetur imperdiet sem laoreet. Quisque maximus 81 | semper ligula at tincidunt. Pellentesque accumsan varius vehicula. 82 |

83 |
84 |
85 | 90 | 124 | 125 | 126 | -------------------------------------------------------------------------------- /assets/index.css: -------------------------------------------------------------------------------- 1 | @import url("https://fonts.googleapis.com/css?family=Poppins"); 2 | @import url("https://fonts.googleapis.com/css?family=Questrial"); 3 | 4 | body { 5 | margin: 0%; 6 | padding: 0%; 7 | width: 100vw; 8 | background: var(--bg-color); 9 | color: var(--text-color); 10 | max-width: 100vw; 11 | overflow-x: hidden; 12 | align-items: center; 13 | font-family: "Poppins", sans-serif; 14 | } 15 | 16 | #loading { 17 | width: 100vw; 18 | height: 100vh; 19 | position: fixed; 20 | background: var(--bg-color); 21 | z-index: 999; 22 | display: flex; 23 | justify-content: center; 24 | flex-direction: column; 25 | align-items: center; 26 | top: 0; 27 | bottom: 0; 28 | left: 0; 29 | right: 0; 30 | } 31 | 32 | #spinner { 33 | animation: rotate 0.5s infinite linear; 34 | width: 50px; 35 | height: 50px; 36 | border: 2px solid var(--bg-color); 37 | border-bottom: 2px solid var(--text-color); 38 | border-radius: 50%; 39 | margin: 0; 40 | } 41 | 42 | @keyframes rotate { 43 | 0% { 44 | transform: rotate(0deg); 45 | } 46 | 47 | 100% { 48 | transform: rotate(360deg); 49 | } 50 | } 51 | 52 | #profile { 53 | width: 24vw; 54 | padding: 4vh 3vw; 55 | height: 92vh; 56 | display: flex; 57 | flex-direction: column; 58 | justify-content: center; 59 | text-align: left; 60 | background: var(--background-image) center center; 61 | background-size: cover !important; 62 | background-repeat: no-repeat; 63 | position: fixed; 64 | color: #fff !important; 65 | } 66 | 67 | #display { 68 | width: 64vw; 69 | padding: 4vh 3vw; 70 | height: 92vh; 71 | display: inline-block; 72 | padding-left: 33vw; 73 | } 74 | 75 | #display h1 { 76 | font-size: 50px; 77 | color: var(--text-color); 78 | font-weight: bold; 79 | font-family: "Questrial", sans-serif; 80 | } 81 | 82 | .emoji { 83 | width: 18px; 84 | height: 18px; 85 | } 86 | 87 | #profile_img_blog { 88 | border-radius: 50%; 89 | width: 90px; 90 | height: 90px; 91 | background-size: cover !important; 92 | background-repeat: no-repeat; 93 | } 94 | 95 | #username_blog { 96 | font-size: 18px; 97 | color: var(--text-color); 98 | font-family: "Poppins", sans-serif; 99 | font-weight: bold; 100 | } 101 | 102 | #username_blog span { 103 | font-size: 24px; 104 | font-family: "Questrial", sans-serif !important; 105 | } 106 | 107 | #username_blog b { 108 | font-size: 12px; 109 | font-family: "Poppins", sans-serif; 110 | font-weight: bold; 111 | } 112 | 113 | #blog-display { 114 | width: 60vw; 115 | margin: 0px 20vw; 116 | text-align: left; 117 | margin-top: 3vh; 118 | z-index: 1; 119 | } 120 | 121 | #profile_blog { 122 | width: 60vw; 123 | margin: 0px 20vw; 124 | margin-top: 34vh; 125 | text-align: left; 126 | z-index: 1; 127 | } 128 | 129 | #background_overlay { 130 | width: 100vw; 131 | height: 55vh; 132 | position: absolute; 133 | z-index: -1; 134 | top: 0; 135 | left: 0; 136 | } 137 | 138 | #background { 139 | width: 100vw; 140 | height: 55vh; 141 | background-size: cover !important; 142 | background-repeat: no-repeat !important; 143 | position: absolute; 144 | z-index: -2; 145 | top: 0; 146 | left: 0; 147 | } 148 | 149 | #blog-display h1 { 150 | font-size: 50px; 151 | color: var(--text-color); 152 | font-weight: bold; 153 | font-family: "Questrial", sans-serif; 154 | } 155 | 156 | #blog-display h2 { 157 | color: var(--blog-gray-color); 158 | } 159 | 160 | #blog-display { 161 | padding: 1vh 0px; 162 | font-family: "Questrial", sans-serif; 163 | } 164 | 165 | #blog p { 166 | font-size: 17px; 167 | line-height: 25px; 168 | word-spacing: 1.2px; 169 | margin: 5vh 0px; 170 | } 171 | 172 | #blog p span { 173 | padding: 2px 4px; 174 | background: var(--text-color); 175 | color: var(--bg-color) !important; 176 | } 177 | 178 | #blog img { 179 | width: 100%; 180 | margin: 2vh 0px; 181 | border-radius: 5px; 182 | border: 1px solid rgb(0, 0, 0, 0.08); 183 | } 184 | 185 | #header { 186 | width: 63vw; 187 | text-align: right; 188 | padding: 3vh 0px; 189 | position: absolute; 190 | } 191 | 192 | #header a { 193 | color: var(--text-color); 194 | text-decoration: none; 195 | margin-left: 4vw; 196 | font-weight: bold; 197 | } 198 | 199 | #footer_blog { 200 | width: 90vw; 201 | padding: 8vh 5vw; 202 | text-align: center; 203 | } 204 | 205 | #footer_blog a { 206 | color: var(--text-color) !important; 207 | text-decoration: none; 208 | font-family: "Questrial", sans-serif; 209 | font-weight: bold; 210 | } 211 | 212 | #footer { 213 | width: 100%; 214 | padding: 8vh 0px; 215 | text-align: center; 216 | } 217 | 218 | #footer a { 219 | color: var(--text-color) !important; 220 | text-decoration: none; 221 | font-family: "Questrial", sans-serif; 222 | font-weight: bold; 223 | } 224 | 225 | #profile_img { 226 | width: 180px; 227 | height: 180px; 228 | min-width: 180px; 229 | min-height: 180px; 230 | max-width: 180px; 231 | max-height: 180px; 232 | border-radius: 5px; 233 | background-size: cover !important; 234 | background-repeat: no-repeat !important; 235 | } 236 | 237 | #profile div { 238 | font-weight: bold; 239 | margin: 1.5vh 0px; 240 | } 241 | 242 | #username { 243 | font-size: 18px; 244 | font-weight: bold; 245 | } 246 | 247 | #username span { 248 | font-size: 24px; 249 | } 250 | 251 | #userbio { 252 | font-size: 26px; 253 | font-family: "Questrial", sans-serif; 254 | width: 100%; 255 | } 256 | 257 | #about { 258 | font-size: 18px; 259 | font-family: "Questrial", sans-serif; 260 | } 261 | 262 | #about a, 263 | #username a { 264 | color: #fff !important; 265 | text-decoration: none; 266 | font-weight: bold; 267 | } 268 | 269 | #about a:hover, 270 | #username a:hover { 271 | text-decoration: underline; 272 | } 273 | 274 | #about span { 275 | margin: 1vh 0px; 276 | display: block; 277 | } 278 | 279 | #about span i { 280 | font-size: 16px; 281 | } 282 | 283 | #work { 284 | margin: 2vh 0px; 285 | padding: 4vh 0px !important; 286 | } 287 | 288 | #forks { 289 | margin: 2vh 0px; 290 | padding: 4vh 0px !important; 291 | } 292 | 293 | .projects { 294 | margin-left: -15px; 295 | /* align section w/ heading above */ 296 | } 297 | 298 | .projects a { 299 | /* 30px is the gutter size in magic grid */ 300 | width: calc(49% - 30px); 301 | /* 49% avoids a weird single column on some wide screens */ 302 | display: flex; 303 | text-decoration: none; 304 | } 305 | 306 | .projects section { 307 | width: 100%; 308 | padding: 2.5vh 5%; 309 | margin: 1vh 0px; 310 | display: inline-block; 311 | border-radius: 5px; 312 | color: var(--text-color); 313 | border: 1px solid rgb(0, 0, 0, 0.08); 314 | box-shadow: 0px 0px 0px rgb(0, 0, 0, 0); 315 | transition: 0.4s ease-in-out; 316 | transform: scale(1); 317 | } 318 | 319 | .projects section:hover { 320 | cursor: pointer; 321 | border: 1px solid rgb(0, 0, 0, 0); 322 | box-shadow: 0px 15px 35px rgb(0, 0, 0, 0.06); 323 | transform: scale(1.03); 324 | } 325 | 326 | .section_title { 327 | font-size: 24px; 328 | font-weight: bold; 329 | margin: 1vh 0px; 330 | padding: 0px 1px; 331 | word-wrap: break-word; 332 | } 333 | 334 | .about_section { 335 | font-size: 18px; 336 | font-family: "Questrial", sans-serif; 337 | margin: 2vh 0px; 338 | font-weight: bold; 339 | word-wrap: break-word; 340 | } 341 | 342 | .bottom_section { 343 | margin: 1vh 0px; 344 | font-size: 14px; 345 | word-wrap: break-word; 346 | } 347 | 348 | .bottom_section span { 349 | margin-right: 20px; 350 | font-weight: bold; 351 | } 352 | 353 | .bottom_section span i { 354 | font-size: 15px; 355 | } 356 | 357 | .socials { 358 | color: #fff; 359 | text-decoration: none; 360 | margin: 3vh 0px !important; 361 | } 362 | 363 | .socials span { 364 | display: inline-block !important; 365 | margin-right: 2vw !important; 366 | font-weight: normal !important; 367 | } 368 | 369 | .socials span a { 370 | font-weight: normal !important; 371 | } 372 | 373 | #blog_section { 374 | margin: 2vh 0px; 375 | padding: 2vh 0px !important; 376 | } 377 | 378 | #blogs { 379 | columns: 2; 380 | } 381 | 382 | #blog_title { 383 | font-size: 50px; 384 | } 385 | 386 | #blog_sub_title { 387 | font-size: 36px; 388 | margin-top: -2vh; 389 | } 390 | 391 | #blogs section { 392 | width: 100%; 393 | display: inline-block; 394 | border-radius: 5px; 395 | color: var(--text-color); 396 | border: 1px solid rgb(0, 0, 0, 0.04); 397 | box-shadow: 0px 0px 0px rgb(0, 0, 0, 0); 398 | transition: 0.4s ease-in-out; 399 | transform: scale(1); 400 | padding: 0px; 401 | margin: 2vh 0px; 402 | } 403 | 404 | #blogs section img { 405 | width: 100%; 406 | border-radius: 5px 5px 0px 0px; 407 | } 408 | 409 | .blog_container { 410 | padding: 2.5vh 5%; 411 | } 412 | 413 | #blogs section:hover { 414 | cursor: pointer; 415 | border: 1px solid rgb(0, 0, 0, 0); 416 | box-shadow: 0px 15px 35px rgb(0, 0, 0, 0.06); 417 | transform: scale(1.03); 418 | } 419 | 420 | .go_back { 421 | position: absolute; 422 | color: var(--text-color); 423 | font-size: 26px; 424 | margin-left: 5vw; 425 | margin-top: 4vh; 426 | } 427 | 428 | ::selection { 429 | color: var(--bg-color); 430 | background: var(--text-color); 431 | } 432 | 433 | @media (max-width: 800px) { 434 | #profile { 435 | width: 90vw; 436 | padding: 4vh 5vw; 437 | height: 60vh; 438 | text-align: center; 439 | position: relative; 440 | } 441 | 442 | #display { 443 | width: 90vw; 444 | padding: 4vh 5vw; 445 | height: auto; 446 | display: inline-block; 447 | padding-left: 5vw; 448 | } 449 | 450 | #profile_img { 451 | width: 120px; 452 | height: 120px; 453 | min-width: 120px; 454 | min-height: 120px; 455 | max-width: 120px; 456 | max-height: 120px; 457 | margin: 0px auto !important; 458 | } 459 | 460 | #work { 461 | margin: 0px; 462 | } 463 | 464 | .projects { 465 | margin-left: 0; 466 | /* remove neg margin to align w/ header */ 467 | } 468 | 469 | .projects a { 470 | width: 100%; 471 | } 472 | 473 | .projects section { 474 | width: 88%; 475 | } 476 | 477 | #blogs { 478 | columns: 1; 479 | } 480 | 481 | #blogs section { 482 | width: 98%; 483 | } 484 | 485 | #blog_section { 486 | margin: 0px; 487 | } 488 | 489 | #blog-display { 490 | width: 90vw; 491 | margin: 0px 5vw; 492 | text-align: left; 493 | margin-top: 0vh; 494 | z-index: 1; 495 | } 496 | 497 | #blog_title { 498 | font-size: 32px !important; 499 | } 500 | 501 | #blog_sub_title { 502 | font-size: 24px; 503 | margin-top: -1vh; 504 | } 505 | 506 | #profile_blog { 507 | width: 90vw; 508 | margin: 0px 5vw; 509 | margin-top: 36vh; 510 | text-align: left; 511 | z-index: 1; 512 | } 513 | 514 | #profile_img_blog { 515 | width: 65px; 516 | height: 65px; 517 | } 518 | 519 | .go_back { 520 | position: relative; 521 | color: var(--text-color); 522 | font-size: 26px; 523 | margin-left: 5vw; 524 | top: 5vh; 525 | } 526 | 527 | #blog img { 528 | margin: 1vh 0px !important; 529 | } 530 | 531 | #blog p { 532 | margin: 2vh 0px; 533 | } 534 | } 535 | 536 | ::-webkit-scrollbar { 537 | width: 5px; 538 | height: 5px; 539 | } 540 | 541 | ::-webkit-scrollbar-track { 542 | background: var(--bg-color); 543 | } 544 | 545 | ::-webkit-scrollbar-thumb { 546 | background: var(--text-color); 547 | } 548 | -------------------------------------------------------------------------------- /assets/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 12 | 18 | 23 | 24 | 25 | 26 | 27 | 28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |

Work.

42 |
43 |
44 | 48 |
49 |

Blog.

50 |
51 |
52 | 57 |
58 | 93 | 94 | 120 | 121 | 122 | -------------------------------------------------------------------------------- /assets/service-worker.js: -------------------------------------------------------------------------------- 1 | importScripts('https://storage.googleapis.com/workbox-cdn/releases/3.6.1/workbox-sw.js'); 2 | 3 | if (workbox) { 4 | workbox.setConfig({ 5 | debug: false 6 | }); 7 | 8 | var defaultStrategy = workbox.strategies.networkFirst({ 9 | cacheName: "fallback", 10 | plugins: [ 11 | new workbox.expiration.Plugin({ 12 | maxEntries: 128, 13 | maxAgeSeconds: 7 * 24 * 60 * 60, // 1 week 14 | purgeOnQuotaError: true, // Opt-in to automatic cleanup 15 | }), 16 | new workbox.cacheableResponse.Plugin({ 17 | statuses: [0, 200] // for opague requests 18 | }), 19 | ], 20 | }); 21 | workbox.routing.setDefaultHandler( 22 | (args) => { 23 | if (args.event.request.method === 'GET') { 24 | return defaultStrategy.handle(args); // use default strategy 25 | } else { 26 | return null 27 | } 28 | } 29 | ); 30 | 31 | workbox.routing.registerRoute( 32 | new RegExp(/.*\.(?:js|css)/g), 33 | workbox.strategies.networkFirst() 34 | ); 35 | 36 | workbox.routing.registerRoute( 37 | new RegExp(/.*\.(?:png|jpg|jpeg|svg|gif|webp)/g), 38 | workbox.strategies.cacheFirst() 39 | ); 40 | } else { 41 | console.log(`No workbox on this browser 😬`); 42 | } -------------------------------------------------------------------------------- /assets/themes/dark.css: -------------------------------------------------------------------------------- 1 | :root { 2 | --bg-color: rgb(10, 10, 10); 3 | --text-color: #fff; 4 | --blog-gray-color: rgb(180, 180, 180); 5 | --background-image: linear-gradient( 6 | 90deg, 7 | rgba(10, 10, 10, 0.3), 8 | rgb(10, 10, 10, 1) 9 | ), 10 | url("{{{background}}}"); 11 | --background-background: linear-gradient( 12 | 0deg, 13 | rgba(10, 10, 10, 1), 14 | rgba(10, 10, 10, 0.6) 15 | ), 16 | url("{{{background}}}") center center fixed; 17 | --height: 50vh; 18 | } 19 | 20 | #display h1 { 21 | -webkit-background-clip: text; 22 | background-clip: text; 23 | -webkit-text-fill-color: #fff; 24 | } 25 | 26 | #blog-display h1 { 27 | -webkit-background-clip: text; 28 | background-clip: text; 29 | -webkit-text-fill-color: #fff; 30 | } 31 | 32 | .projects section { 33 | background: rgb(20, 20, 20); 34 | } 35 | 36 | #blog_section section { 37 | background: rgb(20, 20, 20); 38 | } 39 | 40 | @media (max-width: 800px) { 41 | :root { 42 | --background-image: linear-gradient( 43 | 0deg, 44 | rgba(10, 10, 10, 1), 45 | rgba(10, 10, 10, 0) 46 | ), 47 | url("{{{background}}}") !important; 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /assets/themes/light.css: -------------------------------------------------------------------------------- 1 | :root { 2 | --bg-color: #fff; 3 | --text-color: rgb(10, 10, 10); 4 | --blog-gray-color: rgb(80, 80, 80); 5 | --background-image: linear-gradient( 6 | 90deg, 7 | rgba(10, 10, 10, 0.4), 8 | rgb(10, 10, 10, 0.4) 9 | ), 10 | url("{{{background}}}"); 11 | --background-background: #fff; 12 | } 13 | -------------------------------------------------------------------------------- /bin/gitfolio.js: -------------------------------------------------------------------------------- 1 | #! /usr/bin/env node 2 | /* Argument parser */ 3 | const program = require("commander"); 4 | 5 | process.env.OUT_DIR = process.env.OUT_DIR || process.cwd(); 6 | 7 | const { buildCommand } = require("../build"); 8 | const { updateCommand } = require("../update"); 9 | const { uiCommand } = require("../ui"); 10 | const { runCommand } = require("../run"); 11 | const { version } = require("../package.json"); 12 | 13 | function collect(val, memo) { 14 | memo.push(val); 15 | return memo; 16 | } 17 | 18 | program 19 | .command("build ") 20 | .description( 21 | "Build site with your GitHub username. This will be used to customize your site" 22 | ) 23 | .option("-t, --theme [theme]", "specify a theme to use", "light") 24 | .option("-b, --background [background]", "set the background image") 25 | .option("-f, --fork", "includes forks with repos") 26 | .option("-s, --sort [sort]", "set default sort for repository", "created") 27 | .option("-o, --order [order]", "set default order on sort", "asc") 28 | .option("-w, --twitter [username]", "specify twitter username") 29 | .option("-l, --linkedin [username]", "specify linkedin username") 30 | .option("-m, --medium [username]", "specify medium username") 31 | .option("-d, --dribbble [username]", "specify dribbble username") 32 | .action(buildCommand); 33 | 34 | program 35 | .command("update") 36 | .description("Update user and repository data") 37 | .action(updateCommand); 38 | 39 | program 40 | .command("ui") 41 | .description("Create and Manage blogs with ease") 42 | .action(uiCommand); 43 | 44 | program 45 | .command("run") 46 | .description("Run build files") 47 | .option("-p, --port [port]", "provide a port for localhost, default is 3000") 48 | .action(runCommand); 49 | 50 | program.on("command:*", () => { 51 | console.log("Unknown Command: " + program.args.join(" ")); 52 | program.help(); 53 | }); 54 | 55 | program 56 | .version(version, "-v --version") 57 | .usage(" [options]") 58 | .parse(process.argv); 59 | 60 | if (program.args.length === 0) program.help(); 61 | -------------------------------------------------------------------------------- /build.js: -------------------------------------------------------------------------------- 1 | /* Filepath utilities */ 2 | const path = require("path"); 3 | /* Promise library */ 4 | const bluebird = require("bluebird"); 5 | const hbs = require("handlebars"); 6 | /* Creates promise-returning async functions 7 | from callback-passed async functions */ 8 | const fs = bluebird.promisifyAll(require("fs")); 9 | const { updateHTML } = require("./populate"); 10 | const { getConfig, outDir } = require("./utils"); 11 | 12 | const assetDir = path.resolve(`${__dirname}/assets/`); 13 | const config = path.join(outDir, "config.json"); 14 | 15 | /** 16 | * Creates the stylesheet used by the site from a template stylesheet. 17 | * 18 | * Theme styles are added to the new stylesheet depending on command line 19 | * arguments. 20 | */ 21 | async function populateCSS({ 22 | theme = "light", 23 | background = "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80" 24 | } = {}) { 25 | /* Get the theme the user requests. Defaults to 'light' */ 26 | theme = `${theme}.css`; 27 | let template = path.resolve(assetDir, "index.css"); 28 | let stylesheet = path.join(outDir, "index.css"); 29 | 30 | try { 31 | await fs.accessAsync(outDir, fs.constants.F_OK); 32 | } catch (err) { 33 | await fs.mkdirAsync(outDir); 34 | } 35 | /* Copy over the template CSS stylesheet */ 36 | await fs.copyFileAsync(template, stylesheet); 37 | 38 | /* Get an array of every available theme */ 39 | let themes = await fs.readdirAsync(path.join(assetDir, "themes")); 40 | 41 | if (!themes.includes(theme)) { 42 | console.error('Error: Requested theme not found. Defaulting to "light".'); 43 | theme = "light"; 44 | } 45 | /* Read in the theme stylesheet */ 46 | let themeSource = await fs.readFileSync(path.join(assetDir, "themes", theme)); 47 | themeSource = themeSource.toString("utf-8"); 48 | let themeTemplate = hbs.compile(themeSource); 49 | let styles = themeTemplate({ 50 | background: `${background}` 51 | }); 52 | /* Add the user-specified styles to the new stylesheet */ 53 | await fs.appendFileAsync(stylesheet, styles); 54 | 55 | /* Update the config file with the user's theme choice */ 56 | const data = await getConfig(); 57 | data[0].theme = theme; 58 | await fs.writeFileAsync(config, JSON.stringify(data, null, " ")); 59 | } 60 | 61 | async function populateConfig(opts) { 62 | const data = await getConfig(); 63 | Object.assign(data[0], opts); 64 | await fs.writeFileAsync(config, JSON.stringify(data, null, " ")); 65 | } 66 | 67 | async function buildCommand(username, program) { 68 | await populateCSS(program); 69 | let types; 70 | if (!program.include || !program.include.length) { 71 | types = ["all"]; 72 | } else { 73 | types = program.include; 74 | } 75 | const opts = { 76 | sort: program.sort, 77 | order: program.order, 78 | includeFork: program.fork ? true : false, 79 | types, 80 | twitter: program.twitter, 81 | linkedin: program.linkedin, 82 | medium: program.medium, 83 | dribbble: program.dribbble 84 | }; 85 | 86 | await populateConfig(opts); 87 | updateHTML(("%s", username), opts); 88 | } 89 | 90 | module.exports = { 91 | buildCommand, 92 | populateCSS, 93 | populateConfig 94 | }; 95 | -------------------------------------------------------------------------------- /default/blog.json: -------------------------------------------------------------------------------- 1 | [] 2 | -------------------------------------------------------------------------------- /default/config.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "username": null, 4 | "name": null, 5 | "userimg": null, 6 | "sort": null, 7 | "order": null, 8 | "includeFork": null, 9 | "theme": "light.css" 10 | } 11 | ] 12 | -------------------------------------------------------------------------------- /package-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "gitfolio", 3 | "version": "0.1.5", 4 | "lockfileVersion": 1, 5 | "requires": true, 6 | "dependencies": { 7 | "@sindresorhus/is": { 8 | "version": "0.14.0", 9 | "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.14.0.tgz", 10 | "integrity": "sha512-9NET910DNaIPngYnLLPeg+Ogzqsi9uM4mSboU5y6p8S5DzMTVEsJZrawi+BoDNUVBa2DhJqQYUFvMDfgU062LQ==" 11 | }, 12 | "@szmarczak/http-timer": { 13 | "version": "1.1.2", 14 | "resolved": "https://registry.npmjs.org/@szmarczak/http-timer/-/http-timer-1.1.2.tgz", 15 | "integrity": "sha512-XIB2XbzHTN6ieIjfIMV9hlVcfPU26s2vafYWQcZHWXHOxiaRZYEDKEwdl129Zyg50+foYV2jCgtrqSA6qNuNSA==", 16 | "requires": { 17 | "defer-to-connect": "^1.0.1" 18 | } 19 | }, 20 | "abab": { 21 | "version": "2.0.0", 22 | "resolved": "https://registry.npmjs.org/abab/-/abab-2.0.0.tgz", 23 | "integrity": "sha512-sY5AXXVZv4Y1VACTtR11UJCPHHudgY5i26Qj5TypE6DKlIApbwb5uqhXcJ5UUGbvZNRh7EeIoW+LrJumBsKp7w==" 24 | }, 25 | "accepts": { 26 | "version": "1.3.7", 27 | "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", 28 | "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", 29 | "requires": { 30 | "mime-types": "~2.1.24", 31 | "negotiator": "0.6.2" 32 | } 33 | }, 34 | "acorn": { 35 | "version": "6.4.1", 36 | "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.4.1.tgz", 37 | "integrity": "sha512-ZVA9k326Nwrj3Cj9jlh3wGFutC2ZornPNARZwsNYqQYgN0EsV2d53w5RN/co65Ohn4sUAUtb1rSUAOD6XN9idA==" 38 | }, 39 | "acorn-globals": { 40 | "version": "4.3.2", 41 | "resolved": "https://registry.npmjs.org/acorn-globals/-/acorn-globals-4.3.2.tgz", 42 | "integrity": "sha512-BbzvZhVtZP+Bs1J1HcwrQe8ycfO0wStkSGxuul3He3GkHOIZ6eTqOkPuw9IP1X3+IkOo4wiJmwkobzXYz4wewQ==", 43 | "requires": { 44 | "acorn": "^6.0.1", 45 | "acorn-walk": "^6.0.1" 46 | } 47 | }, 48 | "acorn-walk": { 49 | "version": "6.1.1", 50 | "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-6.1.1.tgz", 51 | "integrity": "sha512-OtUw6JUTgxA2QoqqmrmQ7F2NYqiBPi/L2jqHyFtllhOUvXYQXf0Z1CYUinIfyT4bTCGmrA7gX9FvHA81uzCoVw==" 52 | }, 53 | "ajv": { 54 | "version": "6.10.2", 55 | "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.2.tgz", 56 | "integrity": "sha512-TXtUUEYHuaTEbLZWIKUr5pmBuhDLy+8KYtPYdcV8qC+pOZL+NKqYwvWSRrVXHn+ZmRRAu8vJTAznH7Oag6RVRw==", 57 | "requires": { 58 | "fast-deep-equal": "^2.0.1", 59 | "fast-json-stable-stringify": "^2.0.0", 60 | "json-schema-traverse": "^0.4.1", 61 | "uri-js": "^4.2.2" 62 | } 63 | }, 64 | "array-equal": { 65 | "version": "1.0.0", 66 | "resolved": "https://registry.npmjs.org/array-equal/-/array-equal-1.0.0.tgz", 67 | "integrity": "sha1-jCpe8kcv2ep0KwTHenUJO6J1fJM=" 68 | }, 69 | "array-flatten": { 70 | "version": "1.1.1", 71 | "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", 72 | "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" 73 | }, 74 | "asn1": { 75 | "version": "0.2.4", 76 | "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", 77 | "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", 78 | "requires": { 79 | "safer-buffer": "~2.1.0" 80 | } 81 | }, 82 | "assert-plus": { 83 | "version": "1.0.0", 84 | "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", 85 | "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" 86 | }, 87 | "async-limiter": { 88 | "version": "1.0.0", 89 | "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", 90 | "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" 91 | }, 92 | "asynckit": { 93 | "version": "0.4.0", 94 | "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", 95 | "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" 96 | }, 97 | "aws-sign2": { 98 | "version": "0.7.0", 99 | "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", 100 | "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" 101 | }, 102 | "aws4": { 103 | "version": "1.8.0", 104 | "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", 105 | "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" 106 | }, 107 | "bcrypt-pbkdf": { 108 | "version": "1.0.2", 109 | "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", 110 | "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", 111 | "requires": { 112 | "tweetnacl": "^0.14.3" 113 | } 114 | }, 115 | "bluebird": { 116 | "version": "3.5.4", 117 | "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.4.tgz", 118 | "integrity": "sha512-FG+nFEZChJrbQ9tIccIfZJBz3J7mLrAhxakAbnrJWn8d7aKOC+LWifa0G+p4ZqKp4y13T7juYvdhq9NzKdsrjw==" 119 | }, 120 | "body-parser": { 121 | "version": "1.19.0", 122 | "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", 123 | "integrity": "sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw==", 124 | "requires": { 125 | "bytes": "3.1.0", 126 | "content-type": "~1.0.4", 127 | "debug": "2.6.9", 128 | "depd": "~1.1.2", 129 | "http-errors": "1.7.2", 130 | "iconv-lite": "0.4.24", 131 | "on-finished": "~2.3.0", 132 | "qs": "6.7.0", 133 | "raw-body": "2.4.0", 134 | "type-is": "~1.6.17" 135 | }, 136 | "dependencies": { 137 | "qs": { 138 | "version": "6.7.0", 139 | "resolved": "https://registry.npmjs.org/qs/-/qs-6.7.0.tgz", 140 | "integrity": "sha512-VCdBRNFTX1fyE7Nb6FYoURo/SPe62QCaAyzJvUjwRaIsc+NePBEniHlvxFmmX56+HZphIGtV0XeCirBtpDrTyQ==" 141 | } 142 | } 143 | }, 144 | "browser-process-hrtime": { 145 | "version": "0.1.3", 146 | "resolved": "https://registry.npmjs.org/browser-process-hrtime/-/browser-process-hrtime-0.1.3.tgz", 147 | "integrity": "sha512-bRFnI4NnjO6cnyLmOV/7PVoDEMJChlcfN0z4s1YMBY989/SvlfMI1lgCnkFUs53e9gQF+w7qu7XdllSTiSl8Aw==" 148 | }, 149 | "bytes": { 150 | "version": "3.1.0", 151 | "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", 152 | "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" 153 | }, 154 | "cacheable-request": { 155 | "version": "6.1.0", 156 | "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-6.1.0.tgz", 157 | "integrity": "sha512-Oj3cAGPCqOZX7Rz64Uny2GYAZNliQSqfbePrgAQ1wKAihYmCUnraBtJtKcGR4xz7wF+LoJC+ssFZvv5BgF9Igg==", 158 | "requires": { 159 | "clone-response": "^1.0.2", 160 | "get-stream": "^5.1.0", 161 | "http-cache-semantics": "^4.0.0", 162 | "keyv": "^3.0.0", 163 | "lowercase-keys": "^2.0.0", 164 | "normalize-url": "^4.1.0", 165 | "responselike": "^1.0.2" 166 | }, 167 | "dependencies": { 168 | "get-stream": { 169 | "version": "5.1.0", 170 | "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-5.1.0.tgz", 171 | "integrity": "sha512-EXr1FOzrzTfGeL0gQdeFEvOMm2mzMOglyiOXSTpPC+iAjAKftbr3jpCMWynogwYnM+eSj9sHGc6wjIcDvYiygw==", 172 | "requires": { 173 | "pump": "^3.0.0" 174 | } 175 | }, 176 | "lowercase-keys": { 177 | "version": "2.0.0", 178 | "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-2.0.0.tgz", 179 | "integrity": "sha512-tqNXrS78oMOE73NMxK4EMLQsQowWf8jKooH9g7xPavRT706R6bkQJ6DY2Te7QukaZsulxa30wQ7bk0pm4XiHmA==" 180 | } 181 | } 182 | }, 183 | "caseless": { 184 | "version": "0.12.0", 185 | "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", 186 | "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" 187 | }, 188 | "clone-response": { 189 | "version": "1.0.2", 190 | "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", 191 | "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", 192 | "requires": { 193 | "mimic-response": "^1.0.0" 194 | } 195 | }, 196 | "combined-stream": { 197 | "version": "1.0.8", 198 | "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", 199 | "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", 200 | "requires": { 201 | "delayed-stream": "~1.0.0" 202 | } 203 | }, 204 | "commander": { 205 | "version": "2.20.0", 206 | "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.0.tgz", 207 | "integrity": "sha512-7j2y+40w61zy6YC2iRNpUe/NwhNyoXrYpHMrSunaMG64nRnaf96zO/KMQR4OyN/UnE5KLyEBnKHd4aG3rskjpQ==" 208 | }, 209 | "content-disposition": { 210 | "version": "0.5.3", 211 | "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.3.tgz", 212 | "integrity": "sha512-ExO0774ikEObIAEV9kDo50o+79VCUdEB6n6lzKgGwupcVeRlhrj3qGAfwq8G6uBJjkqLrhT0qEYFcWng8z1z0g==", 213 | "requires": { 214 | "safe-buffer": "5.1.2" 215 | } 216 | }, 217 | "content-type": { 218 | "version": "1.0.4", 219 | "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", 220 | "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" 221 | }, 222 | "cookie": { 223 | "version": "0.4.0", 224 | "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.4.0.tgz", 225 | "integrity": "sha512-+Hp8fLp57wnUSt0tY0tHEXh4voZRDnoIrZPqlo3DPiI4y9lwg/jqx+1Om94/W6ZaPDOUbnjOt/99w66zk+l1Xg==" 226 | }, 227 | "cookie-signature": { 228 | "version": "1.0.6", 229 | "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", 230 | "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" 231 | }, 232 | "core-util-is": { 233 | "version": "1.0.2", 234 | "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", 235 | "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" 236 | }, 237 | "cssom": { 238 | "version": "0.3.6", 239 | "resolved": "https://registry.npmjs.org/cssom/-/cssom-0.3.6.tgz", 240 | "integrity": "sha512-DtUeseGk9/GBW0hl0vVPpU22iHL6YB5BUX7ml1hB+GMpo0NX5G4voX3kdWiMSEguFtcW3Vh3djqNF4aIe6ne0A==" 241 | }, 242 | "cssstyle": { 243 | "version": "1.2.2", 244 | "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-1.2.2.tgz", 245 | "integrity": "sha512-43wY3kl1CVQSvL7wUY1qXkxVGkStjpkDmVjiIKX8R97uhajy8Bybay78uOtqvh7Q5GK75dNPfW0geWjE6qQQow==", 246 | "requires": { 247 | "cssom": "0.3.x" 248 | } 249 | }, 250 | "dashdash": { 251 | "version": "1.14.1", 252 | "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", 253 | "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", 254 | "requires": { 255 | "assert-plus": "^1.0.0" 256 | } 257 | }, 258 | "data-urls": { 259 | "version": "1.1.0", 260 | "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-1.1.0.tgz", 261 | "integrity": "sha512-YTWYI9se1P55u58gL5GkQHW4P6VJBJ5iBT+B5a7i2Tjadhv52paJG0qHX4A0OR6/t52odI64KP2YvFpkDOi3eQ==", 262 | "requires": { 263 | "abab": "^2.0.0", 264 | "whatwg-mimetype": "^2.2.0", 265 | "whatwg-url": "^7.0.0" 266 | } 267 | }, 268 | "debug": { 269 | "version": "2.6.9", 270 | "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", 271 | "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", 272 | "requires": { 273 | "ms": "2.0.0" 274 | } 275 | }, 276 | "decompress-response": { 277 | "version": "3.3.0", 278 | "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", 279 | "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", 280 | "requires": { 281 | "mimic-response": "^1.0.0" 282 | } 283 | }, 284 | "deep-is": { 285 | "version": "0.1.3", 286 | "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", 287 | "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=" 288 | }, 289 | "defer-to-connect": { 290 | "version": "1.0.2", 291 | "resolved": "https://registry.npmjs.org/defer-to-connect/-/defer-to-connect-1.0.2.tgz", 292 | "integrity": "sha512-k09hcQcTDY+cwgiwa6PYKLm3jlagNzQ+RSvhjzESOGOx+MNOuXkxTfEvPrO1IOQ81tArCFYQgi631clB70RpQw==" 293 | }, 294 | "delayed-stream": { 295 | "version": "1.0.0", 296 | "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", 297 | "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" 298 | }, 299 | "depd": { 300 | "version": "1.1.2", 301 | "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", 302 | "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" 303 | }, 304 | "destroy": { 305 | "version": "1.0.4", 306 | "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", 307 | "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" 308 | }, 309 | "domexception": { 310 | "version": "1.0.1", 311 | "resolved": "https://registry.npmjs.org/domexception/-/domexception-1.0.1.tgz", 312 | "integrity": "sha512-raigMkn7CJNNo6Ihro1fzG7wr3fHuYVytzquZKX5n0yizGsTcYgzdIUwj1X9pK0VvjeihV+XiclP+DjwbsSKug==", 313 | "requires": { 314 | "webidl-conversions": "^4.0.2" 315 | } 316 | }, 317 | "duplexer3": { 318 | "version": "0.1.4", 319 | "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", 320 | "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" 321 | }, 322 | "ecc-jsbn": { 323 | "version": "0.1.2", 324 | "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", 325 | "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", 326 | "requires": { 327 | "jsbn": "~0.1.0", 328 | "safer-buffer": "^2.1.0" 329 | } 330 | }, 331 | "ee-first": { 332 | "version": "1.1.1", 333 | "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", 334 | "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" 335 | }, 336 | "ejs": { 337 | "version": "2.6.2", 338 | "resolved": "https://registry.npmjs.org/ejs/-/ejs-2.6.2.tgz", 339 | "integrity": "sha512-PcW2a0tyTuPHz3tWyYqtK6r1fZ3gp+3Sop8Ph+ZYN81Ob5rwmbHEzaqs10N3BEsaGTkh/ooniXK+WwszGlc2+Q==" 340 | }, 341 | "encodeurl": { 342 | "version": "1.0.2", 343 | "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", 344 | "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" 345 | }, 346 | "end-of-stream": { 347 | "version": "1.4.1", 348 | "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.1.tgz", 349 | "integrity": "sha512-1MkrZNvWTKCaigbn+W15elq2BB/L22nqrSY5DKlo3X6+vclJm8Bb5djXJBmEX6fS3+zCh/F4VBK5Z2KxJt4s2Q==", 350 | "requires": { 351 | "once": "^1.4.0" 352 | } 353 | }, 354 | "escape-html": { 355 | "version": "1.0.3", 356 | "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", 357 | "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" 358 | }, 359 | "escodegen": { 360 | "version": "1.11.1", 361 | "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.11.1.tgz", 362 | "integrity": "sha512-JwiqFD9KdGVVpeuRa68yU3zZnBEOcPs0nKW7wZzXky8Z7tffdYUHbe11bPCV5jYlK6DVdKLWLm0f5I/QlL0Kmw==", 363 | "requires": { 364 | "esprima": "^3.1.3", 365 | "estraverse": "^4.2.0", 366 | "esutils": "^2.0.2", 367 | "optionator": "^0.8.1", 368 | "source-map": "~0.6.1" 369 | } 370 | }, 371 | "esprima": { 372 | "version": "3.1.3", 373 | "resolved": "https://registry.npmjs.org/esprima/-/esprima-3.1.3.tgz", 374 | "integrity": "sha1-/cpRzuYTOJXjyI1TXOSdv/YqRjM=" 375 | }, 376 | "estraverse": { 377 | "version": "4.2.0", 378 | "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", 379 | "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=" 380 | }, 381 | "esutils": { 382 | "version": "2.0.2", 383 | "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", 384 | "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=" 385 | }, 386 | "etag": { 387 | "version": "1.8.1", 388 | "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", 389 | "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" 390 | }, 391 | "express": { 392 | "version": "4.17.0", 393 | "resolved": "https://registry.npmjs.org/express/-/express-4.17.0.tgz", 394 | "integrity": "sha512-1Z7/t3Z5ZnBG252gKUPyItc4xdeaA0X934ca2ewckAsVsw9EG71i++ZHZPYnus8g/s5Bty8IMpSVEuRkmwwPRQ==", 395 | "requires": { 396 | "accepts": "~1.3.7", 397 | "array-flatten": "1.1.1", 398 | "body-parser": "1.19.0", 399 | "content-disposition": "0.5.3", 400 | "content-type": "~1.0.4", 401 | "cookie": "0.4.0", 402 | "cookie-signature": "1.0.6", 403 | "debug": "2.6.9", 404 | "depd": "~1.1.2", 405 | "encodeurl": "~1.0.2", 406 | "escape-html": "~1.0.3", 407 | "etag": "~1.8.1", 408 | "finalhandler": "~1.1.2", 409 | "fresh": "0.5.2", 410 | "merge-descriptors": "1.0.1", 411 | "methods": "~1.1.2", 412 | "on-finished": "~2.3.0", 413 | "parseurl": "~1.3.3", 414 | "path-to-regexp": "0.1.7", 415 | "proxy-addr": "~2.0.5", 416 | "qs": "6.7.0", 417 | "range-parser": "~1.2.1", 418 | "safe-buffer": "5.1.2", 419 | "send": "0.17.1", 420 | "serve-static": "1.14.1", 421 | "setprototypeof": "1.1.1", 422 | "statuses": "~1.5.0", 423 | "type-is": "~1.6.18", 424 | "utils-merge": "1.0.1", 425 | "vary": "~1.1.2" 426 | }, 427 | "dependencies": { 428 | "qs": { 429 | "version": "6.7.0", 430 | "resolved": "https://registry.npmjs.org/qs/-/qs-6.7.0.tgz", 431 | "integrity": "sha512-VCdBRNFTX1fyE7Nb6FYoURo/SPe62QCaAyzJvUjwRaIsc+NePBEniHlvxFmmX56+HZphIGtV0XeCirBtpDrTyQ==" 432 | } 433 | } 434 | }, 435 | "extend": { 436 | "version": "3.0.2", 437 | "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", 438 | "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" 439 | }, 440 | "extsprintf": { 441 | "version": "1.3.0", 442 | "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", 443 | "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" 444 | }, 445 | "fast-deep-equal": { 446 | "version": "2.0.1", 447 | "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", 448 | "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" 449 | }, 450 | "fast-json-stable-stringify": { 451 | "version": "2.0.0", 452 | "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", 453 | "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" 454 | }, 455 | "fast-levenshtein": { 456 | "version": "2.0.6", 457 | "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", 458 | "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=" 459 | }, 460 | "finalhandler": { 461 | "version": "1.1.2", 462 | "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", 463 | "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", 464 | "requires": { 465 | "debug": "2.6.9", 466 | "encodeurl": "~1.0.2", 467 | "escape-html": "~1.0.3", 468 | "on-finished": "~2.3.0", 469 | "parseurl": "~1.3.3", 470 | "statuses": "~1.5.0", 471 | "unpipe": "~1.0.0" 472 | } 473 | }, 474 | "forever-agent": { 475 | "version": "0.6.1", 476 | "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", 477 | "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" 478 | }, 479 | "form-data": { 480 | "version": "2.3.3", 481 | "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", 482 | "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", 483 | "requires": { 484 | "asynckit": "^0.4.0", 485 | "combined-stream": "^1.0.6", 486 | "mime-types": "^2.1.12" 487 | } 488 | }, 489 | "forwarded": { 490 | "version": "0.1.2", 491 | "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", 492 | "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" 493 | }, 494 | "fresh": { 495 | "version": "0.5.2", 496 | "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", 497 | "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" 498 | }, 499 | "get-stream": { 500 | "version": "4.1.0", 501 | "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz", 502 | "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==", 503 | "requires": { 504 | "pump": "^3.0.0" 505 | } 506 | }, 507 | "getpass": { 508 | "version": "0.1.7", 509 | "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", 510 | "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", 511 | "requires": { 512 | "assert-plus": "^1.0.0" 513 | } 514 | }, 515 | "github-emoji": { 516 | "version": "1.1.1", 517 | "resolved": "https://registry.npmjs.org/github-emoji/-/github-emoji-1.1.1.tgz", 518 | "integrity": "sha512-SxiGZf8wfMRwg8QwQlHwKMjR7oyy2H3iCpXRzOTp4Mq/xNTNgV9Yi6Y6zwk0Aty6ZUpRC3oJS+Ya5Dgb+DVTiA==" 519 | }, 520 | "got": { 521 | "version": "9.6.0", 522 | "resolved": "https://registry.npmjs.org/got/-/got-9.6.0.tgz", 523 | "integrity": "sha512-R7eWptXuGYxwijs0eV+v3o6+XH1IqVK8dJOEecQfTmkncw9AV4dcw/Dhxi8MdlqPthxxpZyizMzyg8RTmEsG+Q==", 524 | "requires": { 525 | "@sindresorhus/is": "^0.14.0", 526 | "@szmarczak/http-timer": "^1.1.2", 527 | "cacheable-request": "^6.0.0", 528 | "decompress-response": "^3.3.0", 529 | "duplexer3": "^0.1.4", 530 | "get-stream": "^4.1.0", 531 | "lowercase-keys": "^1.0.1", 532 | "mimic-response": "^1.0.1", 533 | "p-cancelable": "^1.0.0", 534 | "to-readable-stream": "^1.0.0", 535 | "url-parse-lax": "^3.0.0" 536 | } 537 | }, 538 | "handlebars": { 539 | "version": "4.5.3", 540 | "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.5.3.tgz", 541 | "integrity": "sha512-3yPecJoJHK/4c6aZhSvxOyG4vJKDshV36VHp0iVCDVh7o9w2vwi3NSnL2MMPj3YdduqaBcu7cGbggJQM0br9xA==", 542 | "requires": { 543 | "neo-async": "^2.6.0", 544 | "optimist": "^0.6.1", 545 | "source-map": "^0.6.1", 546 | "uglify-js": "^3.1.4" 547 | } 548 | }, 549 | "har-schema": { 550 | "version": "2.0.0", 551 | "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", 552 | "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" 553 | }, 554 | "har-validator": { 555 | "version": "5.1.3", 556 | "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", 557 | "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", 558 | "requires": { 559 | "ajv": "^6.5.5", 560 | "har-schema": "^2.0.0" 561 | } 562 | }, 563 | "html-encoding-sniffer": { 564 | "version": "1.0.2", 565 | "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-1.0.2.tgz", 566 | "integrity": "sha512-71lZziiDnsuabfdYiUeWdCVyKuqwWi23L8YeIgV9jSSZHCtb6wB1BKWooH7L3tn4/FuZJMVWyNaIDr4RGmaSYw==", 567 | "requires": { 568 | "whatwg-encoding": "^1.0.1" 569 | } 570 | }, 571 | "http-cache-semantics": { 572 | "version": "4.0.3", 573 | "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.0.3.tgz", 574 | "integrity": "sha512-TcIMG3qeVLgDr1TEd2XvHaTnMPwYQUQMIBLy+5pLSDKYFc7UIqj39w8EGzZkaxoLv/l2K8HaI0t5AVA+YYgUew==" 575 | }, 576 | "http-errors": { 577 | "version": "1.7.2", 578 | "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", 579 | "integrity": "sha512-uUQBt3H/cSIVfch6i1EuPNy/YsRSOUBXTVfZ+yR7Zjez3qjBz6i9+i4zjNaoqcoFVI4lQJ5plg63TvGfRSDCRg==", 580 | "requires": { 581 | "depd": "~1.1.2", 582 | "inherits": "2.0.3", 583 | "setprototypeof": "1.1.1", 584 | "statuses": ">= 1.5.0 < 2", 585 | "toidentifier": "1.0.0" 586 | } 587 | }, 588 | "http-signature": { 589 | "version": "1.2.0", 590 | "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", 591 | "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", 592 | "requires": { 593 | "assert-plus": "^1.0.0", 594 | "jsprim": "^1.2.2", 595 | "sshpk": "^1.7.0" 596 | } 597 | }, 598 | "iconv-lite": { 599 | "version": "0.4.24", 600 | "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", 601 | "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", 602 | "requires": { 603 | "safer-buffer": ">= 2.1.2 < 3" 604 | } 605 | }, 606 | "inherits": { 607 | "version": "2.0.3", 608 | "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", 609 | "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" 610 | }, 611 | "ipaddr.js": { 612 | "version": "1.9.0", 613 | "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.0.tgz", 614 | "integrity": "sha512-M4Sjn6N/+O6/IXSJseKqHoFc+5FdGJ22sXqnjTpdZweHK64MzEPAyQZyEU3R/KRv2GLoa7nNtg/C2Ev6m7z+eA==" 615 | }, 616 | "is-typedarray": { 617 | "version": "1.0.0", 618 | "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", 619 | "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" 620 | }, 621 | "isstream": { 622 | "version": "0.1.2", 623 | "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", 624 | "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" 625 | }, 626 | "jsbn": { 627 | "version": "0.1.1", 628 | "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", 629 | "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" 630 | }, 631 | "jsdom": { 632 | "version": "15.1.0", 633 | "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-15.1.0.tgz", 634 | "integrity": "sha512-QEmc2XIkNfCK3KRfa9ljMJjC4kAGdVgRrs/pCBsQG/QoKz0B42+C58f6TdAmhq/rw494eFCoLHxX6+hWuxb96Q==", 635 | "requires": { 636 | "abab": "^2.0.0", 637 | "acorn": "^6.0.4", 638 | "acorn-globals": "^4.3.0", 639 | "array-equal": "^1.0.0", 640 | "cssom": "^0.3.4", 641 | "cssstyle": "^1.1.1", 642 | "data-urls": "^1.1.0", 643 | "domexception": "^1.0.1", 644 | "escodegen": "^1.11.0", 645 | "html-encoding-sniffer": "^1.0.2", 646 | "nwsapi": "^2.1.3", 647 | "parse5": "5.1.0", 648 | "pn": "^1.1.0", 649 | "request": "^2.88.0", 650 | "request-promise-native": "^1.0.5", 651 | "saxes": "^3.1.9", 652 | "symbol-tree": "^3.2.2", 653 | "tough-cookie": "^2.5.0", 654 | "w3c-hr-time": "^1.0.1", 655 | "w3c-xmlserializer": "^1.1.2", 656 | "webidl-conversions": "^4.0.2", 657 | "whatwg-encoding": "^1.0.5", 658 | "whatwg-mimetype": "^2.3.0", 659 | "whatwg-url": "^7.0.0", 660 | "ws": "^6.1.2", 661 | "xml-name-validator": "^3.0.0" 662 | } 663 | }, 664 | "json-buffer": { 665 | "version": "3.0.0", 666 | "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", 667 | "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" 668 | }, 669 | "json-schema": { 670 | "version": "0.2.3", 671 | "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", 672 | "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" 673 | }, 674 | "json-schema-traverse": { 675 | "version": "0.4.1", 676 | "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", 677 | "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" 678 | }, 679 | "json-stringify-safe": { 680 | "version": "5.0.1", 681 | "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", 682 | "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" 683 | }, 684 | "jsprim": { 685 | "version": "1.4.1", 686 | "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", 687 | "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", 688 | "requires": { 689 | "assert-plus": "1.0.0", 690 | "extsprintf": "1.3.0", 691 | "json-schema": "0.2.3", 692 | "verror": "1.10.0" 693 | } 694 | }, 695 | "keyv": { 696 | "version": "3.1.0", 697 | "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.1.0.tgz", 698 | "integrity": "sha512-9ykJ/46SN/9KPM/sichzQ7OvXyGDYKGTaDlKMGCAlg2UK8KRy4jb0d8sFc+0Tt0YYnThq8X2RZgCg74RPxgcVA==", 699 | "requires": { 700 | "json-buffer": "3.0.0" 701 | } 702 | }, 703 | "levn": { 704 | "version": "0.3.0", 705 | "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", 706 | "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", 707 | "requires": { 708 | "prelude-ls": "~1.1.2", 709 | "type-check": "~0.3.2" 710 | } 711 | }, 712 | "lodash": { 713 | "version": "4.17.19", 714 | "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.19.tgz", 715 | "integrity": "sha512-JNvd8XER9GQX0v2qJgsaN/mzFCNA5BRe/j8JN9d+tWyGLSodKQHKFicdwNYzWwI3wjRnaKPsGj1XkBjx/F96DQ==" 716 | }, 717 | "lodash.sortby": { 718 | "version": "4.7.0", 719 | "resolved": "https://registry.npmjs.org/lodash.sortby/-/lodash.sortby-4.7.0.tgz", 720 | "integrity": "sha1-7dFMgk4sycHgsKG0K7UhBRakJDg=" 721 | }, 722 | "lowercase-keys": { 723 | "version": "1.0.1", 724 | "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", 725 | "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==" 726 | }, 727 | "media-typer": { 728 | "version": "0.3.0", 729 | "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", 730 | "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" 731 | }, 732 | "merge-descriptors": { 733 | "version": "1.0.1", 734 | "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", 735 | "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" 736 | }, 737 | "methods": { 738 | "version": "1.1.2", 739 | "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", 740 | "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" 741 | }, 742 | "mime": { 743 | "version": "1.6.0", 744 | "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", 745 | "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==" 746 | }, 747 | "mime-db": { 748 | "version": "1.40.0", 749 | "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", 750 | "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" 751 | }, 752 | "mime-types": { 753 | "version": "2.1.24", 754 | "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", 755 | "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", 756 | "requires": { 757 | "mime-db": "1.40.0" 758 | } 759 | }, 760 | "mimic-response": { 761 | "version": "1.0.1", 762 | "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", 763 | "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" 764 | }, 765 | "minimist": { 766 | "version": "0.0.10", 767 | "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.10.tgz", 768 | "integrity": "sha1-3j+YVD2/lggr5IrRoMfNqDYwHc8=" 769 | }, 770 | "ms": { 771 | "version": "2.0.0", 772 | "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", 773 | "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" 774 | }, 775 | "ncp": { 776 | "version": "2.0.0", 777 | "resolved": "https://registry.npmjs.org/ncp/-/ncp-2.0.0.tgz", 778 | "integrity": "sha1-GVoh1sRuNh0vsSgbo4uR6d9727M=" 779 | }, 780 | "negotiator": { 781 | "version": "0.6.2", 782 | "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", 783 | "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" 784 | }, 785 | "neo-async": { 786 | "version": "2.6.2", 787 | "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.2.tgz", 788 | "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==" 789 | }, 790 | "normalize-url": { 791 | "version": "4.3.0", 792 | "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-4.3.0.tgz", 793 | "integrity": "sha512-0NLtR71o4k6GLP+mr6Ty34c5GA6CMoEsncKJxvQd8NzPxaHRJNnb5gZE8R1XF4CPIS7QPHLJ74IFszwtNVAHVQ==" 794 | }, 795 | "nwsapi": { 796 | "version": "2.1.4", 797 | "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.1.4.tgz", 798 | "integrity": "sha512-iGfd9Y6SFdTNldEy2L0GUhcarIutFmk+MPWIn9dmj8NMIup03G08uUF2KGbbmv/Ux4RT0VZJoP/sVbWA6d/VIw==" 799 | }, 800 | "oauth-sign": { 801 | "version": "0.9.0", 802 | "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", 803 | "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" 804 | }, 805 | "on-finished": { 806 | "version": "2.3.0", 807 | "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", 808 | "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", 809 | "requires": { 810 | "ee-first": "1.1.1" 811 | } 812 | }, 813 | "once": { 814 | "version": "1.4.0", 815 | "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", 816 | "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", 817 | "requires": { 818 | "wrappy": "1" 819 | } 820 | }, 821 | "optimist": { 822 | "version": "0.6.1", 823 | "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", 824 | "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", 825 | "requires": { 826 | "minimist": "~0.0.1", 827 | "wordwrap": "~0.0.2" 828 | }, 829 | "dependencies": { 830 | "wordwrap": { 831 | "version": "0.0.3", 832 | "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", 833 | "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=" 834 | } 835 | } 836 | }, 837 | "optionator": { 838 | "version": "0.8.2", 839 | "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", 840 | "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", 841 | "requires": { 842 | "deep-is": "~0.1.3", 843 | "fast-levenshtein": "~2.0.4", 844 | "levn": "~0.3.0", 845 | "prelude-ls": "~1.1.2", 846 | "type-check": "~0.3.2", 847 | "wordwrap": "~1.0.0" 848 | } 849 | }, 850 | "p-cancelable": { 851 | "version": "1.1.0", 852 | "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-1.1.0.tgz", 853 | "integrity": "sha512-s73XxOZ4zpt1edZYZzvhqFa6uvQc1vwUa0K0BdtIZgQMAJj9IbebH+JkgKZc9h+B05PKHLOTl4ajG1BmNrVZlw==" 854 | }, 855 | "parse5": { 856 | "version": "5.1.0", 857 | "resolved": "https://registry.npmjs.org/parse5/-/parse5-5.1.0.tgz", 858 | "integrity": "sha512-fxNG2sQjHvlVAYmzBZS9YlDp6PTSSDwa98vkD4QgVDDCAo84z5X1t5XyJQ62ImdLXx5NdIIfihey6xpum9/gRQ==" 859 | }, 860 | "parseurl": { 861 | "version": "1.3.3", 862 | "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", 863 | "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" 864 | }, 865 | "path-to-regexp": { 866 | "version": "0.1.7", 867 | "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", 868 | "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" 869 | }, 870 | "performance-now": { 871 | "version": "2.1.0", 872 | "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", 873 | "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" 874 | }, 875 | "pn": { 876 | "version": "1.1.0", 877 | "resolved": "https://registry.npmjs.org/pn/-/pn-1.1.0.tgz", 878 | "integrity": "sha512-2qHaIQr2VLRFoxe2nASzsV6ef4yOOH+Fi9FBOVH6cqeSgUnoyySPZkxzLuzd+RYOQTRpROA0ztTMqxROKSb/nA==" 879 | }, 880 | "prelude-ls": { 881 | "version": "1.1.2", 882 | "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", 883 | "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=" 884 | }, 885 | "prepend-http": { 886 | "version": "2.0.0", 887 | "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", 888 | "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" 889 | }, 890 | "prettier": { 891 | "version": "1.18.2", 892 | "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.18.2.tgz", 893 | "integrity": "sha512-OeHeMc0JhFE9idD4ZdtNibzY0+TPHSpSSb9h8FqtP+YnoZZ1sl8Vc9b1sasjfymH3SonAF4QcA2+mzHPhMvIiw==" 894 | }, 895 | "proxy-addr": { 896 | "version": "2.0.5", 897 | "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.5.tgz", 898 | "integrity": "sha512-t/7RxHXPH6cJtP0pRG6smSr9QJidhB+3kXu0KgXnbGYMgzEnUxRQ4/LDdfOwZEMyIh3/xHb8PX3t+lfL9z+YVQ==", 899 | "requires": { 900 | "forwarded": "~0.1.2", 901 | "ipaddr.js": "1.9.0" 902 | } 903 | }, 904 | "psl": { 905 | "version": "1.1.31", 906 | "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", 907 | "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" 908 | }, 909 | "pump": { 910 | "version": "3.0.0", 911 | "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz", 912 | "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==", 913 | "requires": { 914 | "end-of-stream": "^1.1.0", 915 | "once": "^1.3.1" 916 | } 917 | }, 918 | "punycode": { 919 | "version": "2.1.1", 920 | "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", 921 | "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" 922 | }, 923 | "qs": { 924 | "version": "6.5.2", 925 | "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", 926 | "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" 927 | }, 928 | "range-parser": { 929 | "version": "1.2.1", 930 | "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", 931 | "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==" 932 | }, 933 | "raw-body": { 934 | "version": "2.4.0", 935 | "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.0.tgz", 936 | "integrity": "sha512-4Oz8DUIwdvoa5qMJelxipzi/iJIi40O5cGV1wNYp5hvZP8ZN0T+jiNkL0QepXs+EsQ9XJ8ipEDoiH70ySUJP3Q==", 937 | "requires": { 938 | "bytes": "3.1.0", 939 | "http-errors": "1.7.2", 940 | "iconv-lite": "0.4.24", 941 | "unpipe": "1.0.0" 942 | } 943 | }, 944 | "request": { 945 | "version": "2.88.0", 946 | "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", 947 | "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", 948 | "requires": { 949 | "aws-sign2": "~0.7.0", 950 | "aws4": "^1.8.0", 951 | "caseless": "~0.12.0", 952 | "combined-stream": "~1.0.6", 953 | "extend": "~3.0.2", 954 | "forever-agent": "~0.6.1", 955 | "form-data": "~2.3.2", 956 | "har-validator": "~5.1.0", 957 | "http-signature": "~1.2.0", 958 | "is-typedarray": "~1.0.0", 959 | "isstream": "~0.1.2", 960 | "json-stringify-safe": "~5.0.1", 961 | "mime-types": "~2.1.19", 962 | "oauth-sign": "~0.9.0", 963 | "performance-now": "^2.1.0", 964 | "qs": "~6.5.2", 965 | "safe-buffer": "^5.1.2", 966 | "tough-cookie": "~2.4.3", 967 | "tunnel-agent": "^0.6.0", 968 | "uuid": "^3.3.2" 969 | }, 970 | "dependencies": { 971 | "punycode": { 972 | "version": "1.4.1", 973 | "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", 974 | "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" 975 | }, 976 | "tough-cookie": { 977 | "version": "2.4.3", 978 | "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", 979 | "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", 980 | "requires": { 981 | "psl": "^1.1.24", 982 | "punycode": "^1.4.1" 983 | } 984 | } 985 | } 986 | }, 987 | "request-promise-core": { 988 | "version": "1.1.2", 989 | "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.2.tgz", 990 | "integrity": "sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag==", 991 | "requires": { 992 | "lodash": "^4.17.11" 993 | } 994 | }, 995 | "request-promise-native": { 996 | "version": "1.0.7", 997 | "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.7.tgz", 998 | "integrity": "sha512-rIMnbBdgNViL37nZ1b3L/VfPOpSi0TqVDQPAvO6U14lMzOLrt5nilxCQqtDKhZeDiW0/hkCXGoQjhgJd/tCh6w==", 999 | "requires": { 1000 | "request-promise-core": "1.1.2", 1001 | "stealthy-require": "^1.1.1", 1002 | "tough-cookie": "^2.3.3" 1003 | } 1004 | }, 1005 | "responselike": { 1006 | "version": "1.0.2", 1007 | "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", 1008 | "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", 1009 | "requires": { 1010 | "lowercase-keys": "^1.0.0" 1011 | } 1012 | }, 1013 | "safe-buffer": { 1014 | "version": "5.1.2", 1015 | "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", 1016 | "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" 1017 | }, 1018 | "safer-buffer": { 1019 | "version": "2.1.2", 1020 | "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", 1021 | "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" 1022 | }, 1023 | "saxes": { 1024 | "version": "3.1.9", 1025 | "resolved": "https://registry.npmjs.org/saxes/-/saxes-3.1.9.tgz", 1026 | "integrity": "sha512-FZeKhJglhJHk7eWG5YM0z46VHmI3KJpMBAQm3xa9meDvd+wevB5GuBB0wc0exPInZiBBHqi00DbS8AcvCGCFMw==", 1027 | "requires": { 1028 | "xmlchars": "^1.3.1" 1029 | } 1030 | }, 1031 | "send": { 1032 | "version": "0.17.1", 1033 | "resolved": "https://registry.npmjs.org/send/-/send-0.17.1.tgz", 1034 | "integrity": "sha512-BsVKsiGcQMFwT8UxypobUKyv7irCNRHk1T0G680vk88yf6LBByGcZJOTJCrTP2xVN6yI+XjPJcNuE3V4fT9sAg==", 1035 | "requires": { 1036 | "debug": "2.6.9", 1037 | "depd": "~1.1.2", 1038 | "destroy": "~1.0.4", 1039 | "encodeurl": "~1.0.2", 1040 | "escape-html": "~1.0.3", 1041 | "etag": "~1.8.1", 1042 | "fresh": "0.5.2", 1043 | "http-errors": "~1.7.2", 1044 | "mime": "1.6.0", 1045 | "ms": "2.1.1", 1046 | "on-finished": "~2.3.0", 1047 | "range-parser": "~1.2.1", 1048 | "statuses": "~1.5.0" 1049 | }, 1050 | "dependencies": { 1051 | "ms": { 1052 | "version": "2.1.1", 1053 | "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", 1054 | "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==" 1055 | } 1056 | } 1057 | }, 1058 | "serve-static": { 1059 | "version": "1.14.1", 1060 | "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.14.1.tgz", 1061 | "integrity": "sha512-JMrvUwE54emCYWlTI+hGrGv5I8dEwmco/00EvkzIIsR7MqrHonbD9pO2MOfFnpFntl7ecpZs+3mW+XbQZu9QCg==", 1062 | "requires": { 1063 | "encodeurl": "~1.0.2", 1064 | "escape-html": "~1.0.3", 1065 | "parseurl": "~1.3.3", 1066 | "send": "0.17.1" 1067 | } 1068 | }, 1069 | "setprototypeof": { 1070 | "version": "1.1.1", 1071 | "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", 1072 | "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" 1073 | }, 1074 | "source-map": { 1075 | "version": "0.6.1", 1076 | "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", 1077 | "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" 1078 | }, 1079 | "sshpk": { 1080 | "version": "1.16.1", 1081 | "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", 1082 | "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", 1083 | "requires": { 1084 | "asn1": "~0.2.3", 1085 | "assert-plus": "^1.0.0", 1086 | "bcrypt-pbkdf": "^1.0.0", 1087 | "dashdash": "^1.12.0", 1088 | "ecc-jsbn": "~0.1.1", 1089 | "getpass": "^0.1.1", 1090 | "jsbn": "~0.1.0", 1091 | "safer-buffer": "^2.0.2", 1092 | "tweetnacl": "~0.14.0" 1093 | } 1094 | }, 1095 | "statuses": { 1096 | "version": "1.5.0", 1097 | "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", 1098 | "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" 1099 | }, 1100 | "stealthy-require": { 1101 | "version": "1.1.1", 1102 | "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", 1103 | "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=" 1104 | }, 1105 | "symbol-tree": { 1106 | "version": "3.2.2", 1107 | "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.2.tgz", 1108 | "integrity": "sha1-rifbOPZgp64uHDt9G8KQgZuFGeY=" 1109 | }, 1110 | "to-readable-stream": { 1111 | "version": "1.0.0", 1112 | "resolved": "https://registry.npmjs.org/to-readable-stream/-/to-readable-stream-1.0.0.tgz", 1113 | "integrity": "sha512-Iq25XBt6zD5npPhlLVXGFN3/gyR2/qODcKNNyTMd4vbm39HUaOiAM4PMq0eMVC/Tkxz+Zjdsc55g9yyz+Yq00Q==" 1114 | }, 1115 | "toidentifier": { 1116 | "version": "1.0.0", 1117 | "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", 1118 | "integrity": "sha512-yaOH/Pk/VEhBWWTlhI+qXxDFXlejDGcQipMlyxda9nthulaxLZUNcUqFxokp0vcYnvteJln5FNQDRrxj3YcbVw==" 1119 | }, 1120 | "tough-cookie": { 1121 | "version": "2.5.0", 1122 | "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.5.0.tgz", 1123 | "integrity": "sha512-nlLsUzgm1kfLXSXfRZMc1KLAugd4hqJHDTvc2hDIwS3mZAfMEuMbc03SujMF+GEcpaX/qboeycw6iO8JwVv2+g==", 1124 | "requires": { 1125 | "psl": "^1.1.28", 1126 | "punycode": "^2.1.1" 1127 | } 1128 | }, 1129 | "tr46": { 1130 | "version": "1.0.1", 1131 | "resolved": "https://registry.npmjs.org/tr46/-/tr46-1.0.1.tgz", 1132 | "integrity": "sha1-qLE/1r/SSJUZZ0zN5VujaTtwbQk=", 1133 | "requires": { 1134 | "punycode": "^2.1.0" 1135 | } 1136 | }, 1137 | "tunnel-agent": { 1138 | "version": "0.6.0", 1139 | "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", 1140 | "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", 1141 | "requires": { 1142 | "safe-buffer": "^5.0.1" 1143 | } 1144 | }, 1145 | "tweetnacl": { 1146 | "version": "0.14.5", 1147 | "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", 1148 | "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" 1149 | }, 1150 | "type-check": { 1151 | "version": "0.3.2", 1152 | "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", 1153 | "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", 1154 | "requires": { 1155 | "prelude-ls": "~1.1.2" 1156 | } 1157 | }, 1158 | "type-is": { 1159 | "version": "1.6.18", 1160 | "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", 1161 | "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", 1162 | "requires": { 1163 | "media-typer": "0.3.0", 1164 | "mime-types": "~2.1.24" 1165 | } 1166 | }, 1167 | "uglify-js": { 1168 | "version": "3.10.3", 1169 | "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.10.3.tgz", 1170 | "integrity": "sha512-Lh00i69Uf6G74mvYpHCI9KVVXLcHW/xu79YTvH7Mkc9zyKUeSPz0owW0dguj0Scavns3ZOh3wY63J0Zb97Za2g==", 1171 | "optional": true 1172 | }, 1173 | "unpipe": { 1174 | "version": "1.0.0", 1175 | "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", 1176 | "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" 1177 | }, 1178 | "uri-js": { 1179 | "version": "4.2.2", 1180 | "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", 1181 | "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", 1182 | "requires": { 1183 | "punycode": "^2.1.0" 1184 | } 1185 | }, 1186 | "url-parse-lax": { 1187 | "version": "3.0.0", 1188 | "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", 1189 | "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", 1190 | "requires": { 1191 | "prepend-http": "^2.0.0" 1192 | } 1193 | }, 1194 | "utils-merge": { 1195 | "version": "1.0.1", 1196 | "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", 1197 | "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" 1198 | }, 1199 | "uuid": { 1200 | "version": "3.3.2", 1201 | "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", 1202 | "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" 1203 | }, 1204 | "vary": { 1205 | "version": "1.1.2", 1206 | "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", 1207 | "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" 1208 | }, 1209 | "verror": { 1210 | "version": "1.10.0", 1211 | "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", 1212 | "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", 1213 | "requires": { 1214 | "assert-plus": "^1.0.0", 1215 | "core-util-is": "1.0.2", 1216 | "extsprintf": "^1.2.0" 1217 | } 1218 | }, 1219 | "w3c-hr-time": { 1220 | "version": "1.0.1", 1221 | "resolved": "https://registry.npmjs.org/w3c-hr-time/-/w3c-hr-time-1.0.1.tgz", 1222 | "integrity": "sha1-gqwr/2PZUOqeMYmlimViX+3xkEU=", 1223 | "requires": { 1224 | "browser-process-hrtime": "^0.1.2" 1225 | } 1226 | }, 1227 | "w3c-xmlserializer": { 1228 | "version": "1.1.2", 1229 | "resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-1.1.2.tgz", 1230 | "integrity": "sha512-p10l/ayESzrBMYWRID6xbuCKh2Fp77+sA0doRuGn4tTIMrrZVeqfpKjXHY+oDh3K4nLdPgNwMTVP6Vp4pvqbNg==", 1231 | "requires": { 1232 | "domexception": "^1.0.1", 1233 | "webidl-conversions": "^4.0.2", 1234 | "xml-name-validator": "^3.0.0" 1235 | } 1236 | }, 1237 | "webidl-conversions": { 1238 | "version": "4.0.2", 1239 | "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-4.0.2.tgz", 1240 | "integrity": "sha512-YQ+BmxuTgd6UXZW3+ICGfyqRyHXVlD5GtQr5+qjiNW7bF0cqrzX500HVXPBOvgXb5YnzDd+h0zqyv61KUD7+Sg==" 1241 | }, 1242 | "whatwg-encoding": { 1243 | "version": "1.0.5", 1244 | "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-1.0.5.tgz", 1245 | "integrity": "sha512-b5lim54JOPN9HtzvK9HFXvBma/rnfFeqsic0hSpjtDbVxR3dJKLc+KB4V6GgiGOvl7CY/KNh8rxSo9DKQrnUEw==", 1246 | "requires": { 1247 | "iconv-lite": "0.4.24" 1248 | } 1249 | }, 1250 | "whatwg-mimetype": { 1251 | "version": "2.3.0", 1252 | "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-2.3.0.tgz", 1253 | "integrity": "sha512-M4yMwr6mAnQz76TbJm914+gPpB/nCwvZbJU28cUD6dR004SAxDLOOSUaB1JDRqLtaOV/vi0IC5lEAGFgrjGv/g==" 1254 | }, 1255 | "whatwg-url": { 1256 | "version": "7.0.0", 1257 | "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-7.0.0.tgz", 1258 | "integrity": "sha512-37GeVSIJ3kn1JgKyjiYNmSLP1yzbpb29jdmwBSgkD9h40/hyrR/OifpVUndji3tmwGgD8qpw7iQu3RSbCrBpsQ==", 1259 | "requires": { 1260 | "lodash.sortby": "^4.7.0", 1261 | "tr46": "^1.0.1", 1262 | "webidl-conversions": "^4.0.2" 1263 | } 1264 | }, 1265 | "wordwrap": { 1266 | "version": "1.0.0", 1267 | "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", 1268 | "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=" 1269 | }, 1270 | "wrappy": { 1271 | "version": "1.0.2", 1272 | "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", 1273 | "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" 1274 | }, 1275 | "ws": { 1276 | "version": "6.2.1", 1277 | "resolved": "https://registry.npmjs.org/ws/-/ws-6.2.1.tgz", 1278 | "integrity": "sha512-GIyAXC2cB7LjvpgMt9EKS2ldqr0MTrORaleiOno6TweZ6r3TKtoFQWay/2PceJ3RuBasOHzXNn5Lrw1X0bEjqA==", 1279 | "requires": { 1280 | "async-limiter": "~1.0.0" 1281 | } 1282 | }, 1283 | "xml-name-validator": { 1284 | "version": "3.0.0", 1285 | "resolved": "https://registry.npmjs.org/xml-name-validator/-/xml-name-validator-3.0.0.tgz", 1286 | "integrity": "sha512-A5CUptxDsvxKJEU3yO6DuWBSJz/qizqzJKOMIfUJHETbBw/sFaDxgd6fxm1ewUaM0jZ444Fc5vC5ROYurg/4Pw==" 1287 | }, 1288 | "xmlchars": { 1289 | "version": "1.3.1", 1290 | "resolved": "https://registry.npmjs.org/xmlchars/-/xmlchars-1.3.1.tgz", 1291 | "integrity": "sha512-tGkGJkN8XqCod7OT+EvGYK5Z4SfDQGD30zAa58OcnAa0RRWgzUEK72tkXhsX1FZd+rgnhRxFtmO+ihkp8LHSkw==" 1292 | } 1293 | } 1294 | } 1295 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "gitfolio", 3 | "version": "0.1.5", 4 | "description": "a portfolio website for everyone to showcase their work", 5 | "main": "build.js", 6 | "bin": "bin/gitfolio.js", 7 | "scripts": { 8 | "cli": "OUT_DIR='./dist' node bin/gitfolio.js", 9 | "clean": "rm -rf ./dist/*", 10 | "prettier": "prettier --write \"./**/*.{js,jsx,json,html,css,md}\"", 11 | "test": "echo \"Error: no test specified\" && exit 1" 12 | }, 13 | "author": { 14 | "name": "@imfunniee and community", 15 | "email": "imfunny@wybemf.com", 16 | "url": "https://imfunniee.github.io" 17 | }, 18 | "bugs": "https://github.com/imfunniee/gitfolio/issues", 19 | "homepage": "https://github.com/imfunniee/gitfolio", 20 | "keywords": [ 21 | "personal-website", 22 | "github", 23 | "portfolio", 24 | "portfolio website", 25 | "blog website", 26 | "blog", 27 | "gitfolio", 28 | "git" 29 | ], 30 | "repository": { 31 | "type": "git", 32 | "url": "https://github.com/imfunniee/gitfolio" 33 | }, 34 | "license": "GPL-3.0", 35 | "dependencies": { 36 | "bluebird": "^3.5.4", 37 | "body-parser": "^1.19.0", 38 | "commander": "^2.20.0", 39 | "ejs": "^2.6.2", 40 | "express": "^4.17.0", 41 | "github-emoji": "^1.1.1", 42 | "got": "^9.6.0", 43 | "handlebars": "^4.1.2", 44 | "jsdom": "^15.1.0", 45 | "ncp": "^2.0.0", 46 | "prettier": "^1.18.2" 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /populate.js: -------------------------------------------------------------------------------- 1 | const fs = require("fs"); 2 | const emoji = require("github-emoji"); 3 | const jsdom = require("jsdom").JSDOM, 4 | options = { 5 | resources: "usable" 6 | }; 7 | const { getConfig, outDir } = require("./utils"); 8 | const { getRepos, getUser } = require("./api"); 9 | 10 | function convertToEmoji(text) { 11 | if (text == null) return; 12 | text = text.toString(); 13 | var pattern = /(?<=:\s*).*?(?=\s*:)/gs; 14 | if (text.match(pattern) != null) { 15 | var str = text.match(pattern); 16 | str = str.filter(function(arr) { 17 | return /\S/.test(arr); 18 | }); 19 | for (i = 0; i < str.length; i++) { 20 | if (emoji.URLS[str[i]] != undefined) { 21 | text = text.replace( 22 | `:${str[i]}:`, 23 | `` 24 | ); 25 | } 26 | } 27 | return text; 28 | } else { 29 | return text; 30 | } 31 | } 32 | 33 | module.exports.updateHTML = (username, opts) => { 34 | const { includeFork, twitter, linkedin, medium, dribbble } = opts; 35 | //add data to assets/index.html 36 | jsdom 37 | .fromFile(`${__dirname}/assets/index.html`, options) 38 | .then(function(dom) { 39 | let window = dom.window, 40 | document = window.document; 41 | (async () => { 42 | try { 43 | console.log("Building HTML/CSS..."); 44 | const repos = await getRepos(username, opts); 45 | 46 | for (var i = 0; i < repos.length; i++) { 47 | let element; 48 | if (repos[i].fork == false) { 49 | element = document.getElementById("work_section"); 50 | } else if (includeFork == true) { 51 | document.getElementById("forks").style.display = "block"; 52 | element = document.getElementById("forks_section"); 53 | } else { 54 | continue; 55 | } 56 | element.innerHTML += ` 57 | 58 |
59 |
${repos[i].name}
60 |
61 | ${convertToEmoji(repos[i].description)} 66 |
67 |
68 |   ${ 73 | repos[i].language 74 | } 75 |   ${ 76 | repos[i].stargazers_count 77 | } 78 |   ${ 79 | repos[i].forks_count 80 | } 81 |
82 |
83 |
`; 84 | } 85 | const user = await getUser(username); 86 | document.title = user.login; 87 | var icon = document.createElement("link"); 88 | icon.setAttribute("rel", "icon"); 89 | icon.setAttribute("href", user.avatar_url); 90 | icon.setAttribute("type", "image/png"); 91 | 92 | document.getElementsByTagName("head")[0].appendChild(icon); 93 | document.getElementById( 94 | "profile_img" 95 | ).style.background = `url('${user.avatar_url}') center center`; 96 | document.getElementById( 97 | "username" 98 | ).innerHTML = `${user.name}@${user.login}`; 101 | //document.getElementById("github_link").href = `https://github.com/${user.login}`; 102 | document.getElementById("userbio").innerHTML = convertToEmoji( 103 | user.bio 104 | ); 105 | document.getElementById("userbio").style.display = 106 | user.bio == null || !user.bio ? "none" : "block"; 107 | document.getElementById("about").innerHTML = ` 108 |   ${user.company} 111 |   ${user.email} 114 |   ${ 117 | user.blog 118 | } 119 |    ${ 122 | user.location 123 | } 124 |    Available for hire 127 |
128 | 131 | 134 | 137 | 140 |
141 | `; 142 | //add data to config.json 143 | const data = await getConfig(); 144 | data[0].username = user.login; 145 | data[0].name = user.name; 146 | data[0].userimg = user.avatar_url; 147 | 148 | await fs.writeFile( 149 | `${outDir}/config.json`, 150 | JSON.stringify(data, null, " "), 151 | function(err) { 152 | if (err) throw err; 153 | console.log("Config file updated."); 154 | } 155 | ); 156 | await fs.writeFile( 157 | `${outDir}/index.html`, 158 | "" + window.document.documentElement.outerHTML, 159 | function(error) { 160 | if (error) throw error; 161 | console.log(`Build Complete, Files can be Found @ ${outDir}\n`); 162 | } 163 | ); 164 | } catch (error) { 165 | console.log(error); 166 | } 167 | })(); 168 | }) 169 | .catch(function(error) { 170 | console.log(error); 171 | }); 172 | }; 173 | -------------------------------------------------------------------------------- /run.js: -------------------------------------------------------------------------------- 1 | const express = require("express"); 2 | const path = require("path"); 3 | const outDir = path.resolve("./dist/" || process.env.OUT_DIR); 4 | const app = express(); 5 | app.use(express.static(`${outDir}`)); 6 | 7 | function runCommand(program) { 8 | let port = program.port ? program.port : 3000; 9 | 10 | app.get("/", function(req, res) { 11 | res.sendFile("/index.html"); 12 | }); 13 | 14 | app.listen(port); 15 | console.log( 16 | `\nGitfolio running on port ${port}, Navigate to http://localhost:${port} in your browser\n` 17 | ); 18 | } 19 | 20 | module.exports = { 21 | runCommand 22 | }; 23 | -------------------------------------------------------------------------------- /ui.js: -------------------------------------------------------------------------------- 1 | const fs = require("fs"); 2 | const express = require("express"); 3 | const { updateHTML } = require("./populate"); 4 | const { populateCSS, populateConfig } = require("./build"); 5 | const { updateCommand } = require("./update"); 6 | const app = express(); 7 | app.set("view engine", "ejs"); 8 | app.use(express.static(__dirname + "/views")); 9 | app.set("views", __dirname + "/views"); 10 | app.use( 11 | express.json({ 12 | limit: "50mb" 13 | }) 14 | ); 15 | app.use( 16 | express.urlencoded({ 17 | limit: "50mb", 18 | extended: true 19 | }) 20 | ); 21 | 22 | const port = 3000; 23 | 24 | const jsdom = require("jsdom").JSDOM, 25 | options = { 26 | resources: "usable" 27 | }; 28 | global.DOMParser = new jsdom().window.DOMParser; 29 | const { getBlog, outDir } = require("./utils"); 30 | 31 | function createBlog(title, subtitle, folder, topImage, images, content) { 32 | // Checks to make sure this directory actually exists 33 | // and creates it if it doesn't 34 | if (!fs.existsSync(`${outDir}/blog/`)) { 35 | fs.mkdirSync( 36 | `${outDir}/blog/`, 37 | { 38 | recursive: true 39 | }, 40 | err => {} 41 | ); 42 | } 43 | 44 | if (!fs.existsSync(`${outDir}/blog/${folder}`)) { 45 | fs.mkdirSync(`${outDir}/blog/${folder}`, { 46 | recursive: true 47 | }); 48 | } 49 | 50 | fs.copyFile( 51 | `${__dirname}/assets/blog/blogTemplate.html`, 52 | `${outDir}/blog/${folder}/index.html`, 53 | err => { 54 | if (err) throw err; 55 | jsdom 56 | .fromFile(`${outDir}/blog/${folder}/index.html`, options) 57 | .then(function(dom) { 58 | let window = dom.window, 59 | document = window.document; 60 | let style = document.createElement("link"); 61 | style.setAttribute("rel", "stylesheet"); 62 | style.setAttribute("href", "../../index.css"); 63 | document.getElementsByTagName("head")[0].appendChild(style); 64 | 65 | document.getElementsByTagName("title")[0].textContent = title; 66 | document.getElementById("blog_title").textContent = title; 67 | document.getElementById("blog_sub_title").textContent = subtitle; 68 | document.getElementById( 69 | "background" 70 | ).style.background = `url('top_image.${ 71 | topImage.split("/")[1].split(";")[0] 72 | }') center center`; 73 | 74 | if (content != null) { 75 | var parser = new DOMParser(); 76 | content = parser.parseFromString(content, "text/html"); 77 | document.getElementById("blog").innerHTML = 78 | content.documentElement.innerHTML; 79 | } 80 | 81 | images = JSON.parse(images); 82 | images.forEach((item, index) => { 83 | var base64Image = item.split(";base64,").pop(); 84 | fs.writeFile( 85 | `${outDir}/blog/${folder}/img_${index}.${ 86 | item.split("/")[1].split(";")[0] 87 | }`, 88 | base64Image, 89 | { 90 | encoding: "base64" 91 | }, 92 | function(err) { 93 | if (err) throw err; 94 | } 95 | ); 96 | }); 97 | 98 | fs.writeFile( 99 | `${outDir}/blog/${folder}/index.html`, 100 | "" + window.document.documentElement.outerHTML, 101 | async function(error) { 102 | if (error) throw error; 103 | 104 | var base64ImageTop = topImage.split(";base64,").pop(); 105 | fs.writeFile( 106 | `${outDir}/blog/${folder}/top_image.${ 107 | topImage.split("/")[1].split(";")[0] 108 | }`, 109 | base64ImageTop, 110 | { 111 | encoding: "base64" 112 | }, 113 | function(err) { 114 | if (err) throw err; 115 | } 116 | ); 117 | 118 | let blog_data = { 119 | url_title: folder, 120 | title: title, 121 | sub_title: subtitle, 122 | top_image: `top_image.${topImage.split("/")[1].split(";")[0]}`, 123 | visible: true 124 | }; 125 | const old_blogs = await getBlog(); 126 | old_blogs.push(blog_data); 127 | fs.writeFile( 128 | `${outDir}/blog.json`, 129 | JSON.stringify(old_blogs, null, " "), 130 | function(err) { 131 | if (err) throw err; 132 | console.log( 133 | `Blog created successfully at ${outDir}\\blog\\${folder}\n` 134 | ); 135 | } 136 | ); 137 | } 138 | ); 139 | }) 140 | .catch(function(error) { 141 | console.log(error); 142 | }); 143 | } 144 | ); 145 | } 146 | 147 | function uiCommand() { 148 | app.get("/", function(req, res) { 149 | res.render("index.ejs"); 150 | }); 151 | 152 | app.get("/update", function(req, res) { 153 | if (!fs.existsSync(`${outDir}/config.json`)) { 154 | return res.send( 155 | 'You need to run build command before using update
Go Back' 156 | ); 157 | } 158 | updateCommand(); 159 | res.redirect("/"); 160 | }); 161 | 162 | app.post("/build", function(req, res) { 163 | let username = req.body.username; 164 | if (!username) { 165 | return res.send("username can't be empty"); 166 | } 167 | let sort = req.body.sort ? req.body.sort : "created"; 168 | let order = req.body.order ? req.body.order : "asc"; 169 | let includeFork = req.body.fork == "true" ? true : false; 170 | let types = ["owner"]; 171 | let twitter = req.body.twitter ? req.body.twitter : null; 172 | let linkedin = req.body.linkedin ? req.body.linkedin : null; 173 | let medium = req.body.medium ? req.body.medium : null; 174 | let dribbble = req.body.dribbble ? req.body.dribbble : null; 175 | let background = req.body.background 176 | ? req.body.background 177 | : "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80"; 178 | let theme = req.body.theme == "on" ? "dark" : "light"; 179 | const opts = { 180 | sort: sort, 181 | order: order, 182 | includeFork: includeFork, 183 | types, 184 | twitter: twitter, 185 | linkedin: linkedin, 186 | medium: medium, 187 | dribbble: dribbble 188 | }; 189 | 190 | updateHTML(username, opts); 191 | populateCSS({ 192 | background: background, 193 | theme: theme 194 | }); 195 | populateConfig(opts); 196 | res.redirect("/"); 197 | }); 198 | 199 | app.get("/blog", function(req, res) { 200 | if (!fs.existsSync(`${outDir}/config.json`)) { 201 | return res.send( 202 | 'You need to run build command before accessing blogs
Go Back' 203 | ); 204 | } 205 | fs.readFile(`${outDir}/config.json`, function(err, data) { 206 | res.render("blog.ejs", { 207 | profile: JSON.parse(data) 208 | }); 209 | }); 210 | }); 211 | 212 | app.post("/createBlog", function(req, res) { 213 | let title = req.body.title; 214 | let subtitle = req.body.subtitle; 215 | let content = req.body.content ? req.body.content : null; 216 | if (!title) { 217 | return res.send("title can't be empty"); 218 | } 219 | if (!subtitle) { 220 | return res.send("subtitle can't be empty"); 221 | } 222 | if (!content) { 223 | return res.send("something isn't working fine, try again :p"); 224 | } 225 | let folder = title.replace(/[^a-zA-Z ]/g, "").replace(/ /g, "-"); 226 | let topImage = req.body.top_image; 227 | let images = req.body.images; 228 | createBlog(title, subtitle, folder, topImage, images, content); 229 | res.redirect("/blog"); 230 | }); 231 | 232 | console.log("\nStarting..."); 233 | app.listen(port); 234 | console.log( 235 | `The GUI is running on port ${port}, Navigate to http://localhost:${port} in your browser\n` 236 | ); 237 | } 238 | 239 | module.exports = { 240 | uiCommand 241 | }; 242 | -------------------------------------------------------------------------------- /update.js: -------------------------------------------------------------------------------- 1 | const { getConfig } = require("./utils"); 2 | const { updateHTML } = require("./populate"); 3 | 4 | async function updateCommand() { 5 | const data = await getConfig(); 6 | var username = data[0].username; 7 | if (username == null) { 8 | console.log( 9 | "username not found in config.json, please run build command before using update" 10 | ); 11 | return; 12 | } 13 | const opts = { 14 | sort: data[0].sort, 15 | order: data[0].order, 16 | includeFork: data[0].includeFork, 17 | types: data[0].types, 18 | twitter: data[0].twitter, 19 | linkedin: data[0].linkedin, 20 | medium: data[0].medium, 21 | dribbble: data[0].dribbble 22 | }; 23 | updateHTML(username, opts); 24 | } 25 | 26 | module.exports = { 27 | updateCommand 28 | }; 29 | -------------------------------------------------------------------------------- /utils.js: -------------------------------------------------------------------------------- 1 | const path = require("path"); 2 | const bluebird = require("bluebird"); 3 | const fs = bluebird.promisifyAll(require("fs")); 4 | 5 | const outDir = path.resolve("./dist/" || process.env.OUT_DIR); 6 | const configPath = path.join(outDir, "config.json"); 7 | const blogPath = path.join(outDir, "blog.json"); 8 | 9 | const defaultConfigPath = path.resolve(`${__dirname}/default/config.json`); 10 | const defaultBlogPath = path.resolve(`${__dirname}/default/blog.json`); 11 | 12 | /** 13 | * Tries to read file from out dir, 14 | * if not present returns default file contents 15 | */ 16 | async function getFileWithDefaults(file, defaultFile) { 17 | try { 18 | await fs.accessAsync(file, fs.constants.F_OK); 19 | } catch (err) { 20 | const defaultData = await fs.readFileAsync(defaultFile); 21 | return JSON.parse(defaultData); 22 | } 23 | const data = await fs.readFileAsync(file); 24 | return JSON.parse(data); 25 | } 26 | 27 | async function getConfig() { 28 | return getFileWithDefaults(configPath, defaultConfigPath); 29 | } 30 | 31 | async function getBlog() { 32 | return getFileWithDefaults(blogPath, defaultBlogPath); 33 | } 34 | 35 | module.exports = { 36 | outDir, 37 | getConfig, 38 | getBlog 39 | }; 40 | -------------------------------------------------------------------------------- /views/blog.ejs: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Gitfolio UI 8 | 12 | 18 | 19 | 23 | 24 | 25 |
26 | gitfolio 27 | New Blog 28 | Update 29 | Home 30 |
31 |
32 | 33 |
34 | 41 | 42 | 43 | 44 | 50 | 58 | 59 | 60 |
45 |
49 |
51 |
52 | <% if(profile[0].name)%> 53 | <%= profile[0].name%> 54 | <% %> 55 |
@<%= profile[0].username%> 56 |
57 |
61 |
62 |
68 | 77 |
78 | 87 | 88 | 89 | 90 | 91 |
92 |
93 | 100 | 107 | 114 |
Tip : You can use html inside paragraphs
115 |
116 | 119 |
120 |
121 | 125 | 258 | 259 | 260 | -------------------------------------------------------------------------------- /views/css/font/Circular.otf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/imfunniee/gitfolio/2f8fd941db3848a4f1e2067004ea96f60ecd8608/views/css/font/Circular.otf -------------------------------------------------------------------------------- /views/css/index.css: -------------------------------------------------------------------------------- 1 | @import url("https://fonts.googleapis.com/css?family=Poppins"); 2 | @import url("https://fonts.googleapis.com/css?family=Questrial"); 3 | 4 | @font-face { 5 | font-family: "Circular"; 6 | src: url("./font/Circular.otf"); 7 | } 8 | 9 | body { 10 | margin: 0%; 11 | padding: 0%; 12 | width: 100vw; 13 | max-width: 100vw; 14 | overflow-x: hidden; 15 | align-items: center; 16 | font-family: "Poppins", sans-serif; 17 | background: rgb(250, 250, 250) !important; 18 | will-change: auto; 19 | } 20 | 21 | header { 22 | width: 90vw; 23 | padding: 4vh 5vw; 24 | font-weight: bold; 25 | background: rgb(255, 255, 255); 26 | font-size: 32px; 27 | } 28 | 29 | header b { 30 | font-family: "Circular", sans-serif; 31 | } 32 | 33 | header a { 34 | font-size: 16px; 35 | margin: 1.8vh 0px; 36 | margin-left: 4vw; 37 | color: #000; 38 | text-decoration: none; 39 | transition: 0.4s ease-in-out; 40 | } 41 | 42 | header a:hover { 43 | color: #bebebe; 44 | } 45 | 46 | form { 47 | width: 90vw; 48 | padding: 2vh 5vw; 49 | } 50 | 51 | form .button { 52 | margin: 2vh 0px; 53 | } 54 | 55 | .input { 56 | margin: 1.5vh 0px !important; 57 | } 58 | 59 | .label { 60 | display: inline-block !important; 61 | margin-right: 25px; 62 | font-weight: bold; 63 | } 64 | 65 | button { 66 | transition: 0.4s ease-in-out !important; 67 | } 68 | 69 | button:hover { 70 | color: #fff; 71 | background: #000 !important; 72 | } 73 | 74 | .-size-small { 75 | margin-right: 1vw !important; 76 | } 77 | 78 | #top_image { 79 | width: 100vw; 80 | height: 50vh; 81 | position: absolute; 82 | top: 14vh; 83 | left: 0; 84 | background: linear-gradient(0deg, rgb(250, 250, 250), rgb(200, 200, 200)); 85 | background-size: cover !important; 86 | background-repeat: no-repeat !important; 87 | z-index: 1; 88 | text-align: right; 89 | } 90 | 91 | #top_image i { 92 | font-size: 20px; 93 | position: absolute; 94 | z-index: 5; 95 | top: 4vh; 96 | right: 5vw; 97 | padding: 15px 15px; 98 | background: #ffffff; 99 | color: rgb(0, 0, 0); 100 | border-radius: 50%; 101 | } 102 | 103 | #top_image i:hover { 104 | cursor: pointer; 105 | } 106 | 107 | #profile_blog { 108 | width: 60vw; 109 | margin: 0px 20vw; 110 | margin-top: 42vh !important; 111 | text-align: left; 112 | z-index: 1; 113 | transition: 0.4s ease-in-out; 114 | z-index: 2; 115 | position: relative; 116 | } 117 | 118 | #profile_img_blog { 119 | border-radius: 50%; 120 | width: 90px; 121 | height: 90px; 122 | background-size: cover !important; 123 | background-repeat: no-repeat; 124 | } 125 | 126 | #username_blog { 127 | font-size: 18px; 128 | color: #000; 129 | font-family: "Poppins", sans-serif; 130 | font-weight: bold; 131 | padding-left: 0px; 132 | } 133 | 134 | #username_blog span { 135 | font-size: 24px; 136 | font-family: "Questrial", sans-serif !important; 137 | } 138 | 139 | #username_blog b { 140 | font-size: 12px; 141 | font-family: "Poppins", sans-serif; 142 | font-weight: bold; 143 | } 144 | 145 | #blog-display { 146 | width: 60vw; 147 | margin: 3vh 20vw; 148 | text-align: left; 149 | z-index: 1; 150 | transition: 0.4s ease-in-out; 151 | z-index: 2; 152 | position: relative; 153 | } 154 | 155 | #blog_title { 156 | font-size: 50px; 157 | color: #000; 158 | font-weight: bold; 159 | font-family: "Questrial", sans-serif; 160 | background: transparent; 161 | border: 0px; 162 | width: 100%; 163 | resize: none; 164 | height: auto; 165 | overflow-y: hidden; 166 | } 167 | 168 | #blog_sub_title { 169 | font-size: 36px; 170 | color: rgb(100, 100, 100); 171 | font-weight: bold; 172 | font-family: "Questrial", sans-serif; 173 | background: transparent; 174 | border: 0px; 175 | width: 100%; 176 | resize: none; 177 | height: auto; 178 | overflow-y: hidden; 179 | } 180 | 181 | #blog_sub_title::placeholder { 182 | color: rgb(100, 100, 100); 183 | } 184 | 185 | #blog-display h2 { 186 | color: var(--blog-gray-color); 187 | } 188 | 189 | #blog-display { 190 | padding: 1vh 0px; 191 | font-family: "Questrial", sans-serif; 192 | } 193 | 194 | .div_for_buttons { 195 | margin-top: 5vh; 196 | } 197 | 198 | .para { 199 | font-size: 17px; 200 | line-height: 25px; 201 | word-spacing: 1.2px; 202 | margin: 5vh 0px; 203 | background: transparent; 204 | border: 0px; 205 | width: 100%; 206 | font-family: "Questrial", sans-serif; 207 | resize: none; 208 | height: auto; 209 | overflow-y: hidden; 210 | } 211 | 212 | .para span { 213 | padding: 2px 4px; 214 | background: #000; 215 | color: #fff !important; 216 | } 217 | 218 | #blog { 219 | margin-top: 2vh; 220 | } 221 | 222 | #blog img { 223 | width: 100%; 224 | margin: 2vh 0px; 225 | border-radius: 5px; 226 | border: 1px solid rgb(0, 0, 0, 0.08); 227 | } 228 | 229 | .remove { 230 | margin-bottom: 2vh 0px; 231 | font-weight: bold; 232 | transition: 0.4s ease-in-out; 233 | font-size: 16px; 234 | } 235 | 236 | .remove i { 237 | font-size: 14px; 238 | margin-right: 3px; 239 | } 240 | 241 | .remove:hover { 242 | cursor: pointer; 243 | color: rgb(255, 70, 70); 244 | } 245 | 246 | @media (max-width: 800px) { 247 | #blog-display { 248 | width: 90vw; 249 | margin: 0px 5vw; 250 | text-align: left; 251 | margin-top: 0vh; 252 | z-index: 1; 253 | } 254 | 255 | #profile_blog { 256 | width: 90vw; 257 | margin: 0px 5vw; 258 | } 259 | 260 | #profile_img_blog { 261 | width: 70px; 262 | height: 70px; 263 | } 264 | 265 | #blog img { 266 | margin: 1vh 0px !important; 267 | } 268 | 269 | #blog p { 270 | margin: 2vh 0px; 271 | } 272 | } 273 | 274 | ::selection { 275 | color: #fff; 276 | background: #000; 277 | } 278 | 279 | ::-webkit-scrollbar { 280 | width: 5px; 281 | height: 5px; 282 | } 283 | 284 | ::-webkit-scrollbar-track { 285 | background: #fff; 286 | } 287 | 288 | ::-webkit-scrollbar-thumb { 289 | background: #000; 290 | } 291 | 292 | input, 293 | textarea:focus { 294 | outline: none; 295 | } 296 | 297 | ::placeholder { 298 | color: #000; 299 | } 300 | -------------------------------------------------------------------------------- /views/index.ejs: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Gitfolio UI 8 | 12 | 18 | 19 | 23 | 24 | 25 |
26 | gitfolio 27 | New Blog 28 | Update 29 | Home 30 |
31 |
32 |

Build or Edit Portfolio

33 |
41 | 48 |

Sort By :

49 | 54 | 55 | 60 | 61 | 66 | 67 | 72 | 73 | 78 | 79 |

Order By :

80 | 85 | 90 |

91 | 96 | 101 | 106 | 136 |

137 | 138 |
139 | 143 | 152 | 153 | 154 | --------------------------------------------------------------------------------