├── .github ├── ISSUE_TEMPLATE │ ├── Bug_report.md │ └── Enhancement.md └── workflows │ └── deploy.yml ├── LICENSE ├── README.md ├── assets └── logo.png ├── package.json ├── template.json └── template ├── .env ├── .eslintrc ├── .prettierrc ├── .vscode └── settings.json ├── README.md ├── craco.config.js ├── gitignore ├── public ├── favicon.ico ├── index.html ├── logo192.png ├── logo512.png ├── manifest.json ├── reset.css └── robots.txt ├── src ├── components │ ├── App.test.tsx │ ├── App.tsx │ └── shared │ │ └── .gitkeep ├── features │ └── index.ts ├── index.tsx ├── react-app-env.d.ts ├── setupTests.ts └── utils │ └── history.ts ├── tsconfig.json └── tsconfig.paths.json /.github/ISSUE_TEMPLATE/Bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🐛 Bug report 3 | about: Report to bug or error! 4 | --- 5 | 6 | ## Description 7 | 8 | ### Bug Environment 9 | 10 | ### Current 11 | 12 | ### Expected 13 | 14 | ### Reference 15 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/Enhancement.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🌈 Enhancement 3 | about: Things you might want to try to improve or add to in your extension. 4 | --- 5 | 6 | ## Description 7 | 8 | ### Request Feature 9 | 10 | ### Reference 11 | -------------------------------------------------------------------------------- /.github/workflows/deploy.yml: -------------------------------------------------------------------------------- 1 | name: Deploy 2 | on: [push] 3 | 4 | jobs: 5 | publish: 6 | runs-on: ubuntu-latest 7 | name: Publish 8 | steps: 9 | - name: Checkout 10 | uses: actions/checkout@v1 11 | 12 | # https://github.com/cycjimmy/semantic-release-action 13 | - name: Semantic Release 14 | uses: cycjimmy/semantic-release-action@v2 15 | id: semantic 16 | with: 17 | branch: master 18 | extra_plugins: | 19 | @semantic-release/git 20 | @semantic-release/changelog 21 | env: 22 | GITHUB_TOKEN: ${{ secrets.GITHUB_ACCESS_TOKEN }} 23 | NPM_TOKEN: ${{ secrets.NPM_TOKEN }} 24 | 25 | - name: Push updates to branch for major version 26 | # if there is a new version published, let's say v1.2.3 27 | # then this step will update branch "v1" to this commit 28 | if: steps.semantic.outputs.new_release_published == 'true' 29 | run: "git push https://x-access-token:${GITHUB_ACCESS_TOKEN}@github.com/${GITHUB_REPOSITORY}.git HEAD:refs/heads/v${{steps.semantic.outputs.new_release_major_version}}" 30 | env: 31 | GITHUB_TOKEN: ${{ secrets.GITHUB_ACCESS_TOKEN }} 32 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019 Jbee 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 |
2 | 3 | 4 | 5 |
6 | 7 | # cra-template-unicorn 8 | 9 | ![GitHub Action Status](https://github.com/JaeYeopHan/cra-template-unicorn/workflows/Deploy/badge.svg) [![semantic-release](https://img.shields.io/badge/%20%20%F0%9F%93%A6%F0%9F%9A%80-semantic--release-e10079.svg)](https://github.com/semantic-release/semantic-release) [![npm version](https://badge.fury.io/js/cra-template-unicorn.svg)](https://badge.fury.io/js/cra-template-unicorn) 10 | 11 | The template for [Create React App](https://github.com/facebook/create-react-app). 12 | 13 | ## Start Template 14 | 15 | ### npx 16 | 17 | ```sh 18 | npx create-react-app my-app --template unicorn 19 | ``` 20 | 21 | ### npm 22 | 23 | ```sh 24 | npm init react-app my-app --template unicorn 25 | ``` 26 | 27 | ### yarn 28 | 29 | ```sh 30 | yarn create react-app my-app --template unicorn 31 | ``` 32 | 33 | ## In this template 34 | 35 | - [TypeScript 3.7.x version](https://github.com/microsoft/TypeScript) 36 | - [craco](https://github.com/gsoft-inc/craco) 37 | - [redux-toolkit](https://github.com/reduxjs/redux-toolkit) 38 | - [react-redux 7.1.x](https://github.com/reduxjs/react-redux) 39 | - [react-router](https://github.com/ReactTraining/react-router) 40 | - [emotion 10.x](https://github.com/emotion-js/emotion) 41 | 42 | ## Support 43 | 44 | - Support absolute path with TypeScript 45 | - Support VSCode Integration 46 | - Support reset.css 47 | - Support prettier 48 | - Support emotion source map 49 | - Customize config with craco 50 | - Customize eslint config > [link](https://create-react-app.dev/docs/advanced-configuration) 51 | 52 | ## Show your support 53 | 54 | Give a ⭐️ if this project helped you! 55 | 56 |
57 | 58 | Written by @Jbee 59 | 60 | 61 |
62 | -------------------------------------------------------------------------------- /assets/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/jbee37142/cra-template-unicorn/f467b79652f038b2dbb492c13823677f582d2c0c/assets/logo.png -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "cra-template-unicorn", 3 | "private": false, 4 | "version": "0.0.1", 5 | "description": "The full template with redux-toolkit for Create React App.", 6 | "main": "template.json", 7 | "scripts": { 8 | "test": "echo \"Error: no test specified\" && exit 1" 9 | }, 10 | "keywords": [ 11 | "cra", 12 | "cra-template", 13 | "redux-toolkit-template" 14 | ], 15 | "author": "Jbee[ljyhanll@gmail.com]", 16 | "engines": { 17 | "node": ">=8" 18 | }, 19 | "repository": { 20 | "type": "git", 21 | "url": "https://github.com/JaeYeopHan/cra-template-unicorn.git" 22 | }, 23 | "bugs": { 24 | "url": "https://github.com/JaeYeopHan/cra-template-unicorn" 25 | }, 26 | "files": [ 27 | "template", 28 | "template.json" 29 | ], 30 | "license": "MIT" 31 | } 32 | -------------------------------------------------------------------------------- /template.json: -------------------------------------------------------------------------------- 1 | { 2 | "dependencies": { 3 | "@craco/craco": "^5.6.4", 4 | "@emotion/core": "^10.0.28", 5 | "@emotion/styled": "^10.0.27", 6 | "@reduxjs/toolkit": "^1.3.6", 7 | "@testing-library/jest-dom": "^5.7.0", 8 | "@testing-library/react": "^10.0.4", 9 | "@testing-library/user-event": "^10.1.2", 10 | "@types/jest": "^25.2.1", 11 | "@types/node": "^13.13.5", 12 | "@types/react": "^16.9.34", 13 | "@types/react-dom": "^16.9.7", 14 | "@types/react-redux": "^7.1.8", 15 | "@types/react-router": "^5.1.7", 16 | "@types/react-router-dom": "^5.1.5", 17 | "babel-plugin-emotion": "^10.0.33", 18 | "eslint-plugin-simple-import-sort": "^5.0.3", 19 | "react": "^16.13.1", 20 | "react-dom": "^16.13.1", 21 | "react-redux": "^7.2.0", 22 | "react-router": "^5.1.2", 23 | "react-router-dom": "^5.1.2", 24 | "react-scripts": "3.4.1", 25 | "typescript": "~3.8.3" 26 | }, 27 | "scripts": { 28 | "start": "craco start", 29 | "build": "craco build", 30 | "test": "craco test", 31 | "lint": "eslint ." 32 | }, 33 | "eslintConfig": { 34 | "extends": "react-app" 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /template/.env: -------------------------------------------------------------------------------- 1 | EXTEND_ESLINT=true -------------------------------------------------------------------------------- /template/.eslintrc: -------------------------------------------------------------------------------- 1 | { 2 | "extends": ["react-app"], 3 | "plugins": ["react-hooks", "simple-import-sort"], 4 | "rules": { 5 | "react-hooks/rules-of-hooks": "error", 6 | "simple-import-sort/sort": "error", 7 | "no-multiple-empty-lines": "error", 8 | "comma-dangle": ["error", "always-multiline"], 9 | "eol-last": ["error", "always"], 10 | "semi": ["error", "never"], 11 | "quotes": ["error", "single"], 12 | "no-tabs": "error", 13 | "padding-line-between-statements": [ 14 | "error", 15 | { "blankLine": "always", "prev": "*", "next": "return" } 16 | ] 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /template/.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "semi": false, 3 | "trailingComma": "all", 4 | "singleQuote": true 5 | } 6 | -------------------------------------------------------------------------------- /template/.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "editor.formatOnSave": true, 3 | "javascript.format.enable": false, 4 | "eslint.alwaysShowStatus": true, 5 | "eslint.options": { 6 | "extensions": [".html", ".ts", ".js", ".tsx"] 7 | }, 8 | "files.autoSaveDelay": 500, 9 | "eslint.packageManager": "yarn", 10 | "typescript.tsdk": "node_modules/typescript/lib", 11 | "editor.codeActionsOnSave": { 12 | "source.fixAll.eslint": true, 13 | "source.organizeImports": true 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /template/README.md: -------------------------------------------------------------------------------- 1 | ![cra-template-unicorn_logo](./assets/logo.png) 2 | 3 | # cra-template-unicorn 4 | 5 | ![GitHub Action Status](https://github.com/JaeYeopHan/cra-template-unicorn/workflows/Deploy/badge.svg) [![semantic-release](https://img.shields.io/badge/%20%20%F0%9F%93%A6%F0%9F%9A%80-semantic--release-e10079.svg)](https://github.com/semantic-release/semantic-release) [![npm version](https://badge.fury.io/js/cra-template-unicorn.svg)](https://badge.fury.io/js/cra-template-unicorn) 6 | 7 | The template for [Create React App](https://github.com/facebook/create-react-app). 8 | 9 | ## Start Template 10 | 11 | ### npx 12 | 13 | ```sh 14 | npx create-react-app my-app --template unicorn 15 | ``` 16 | 17 | ### npm 18 | 19 | ```sh 20 | npm init react-app my-app --template unicorn 21 | ``` 22 | 23 | ### yarn 24 | 25 | ```sh 26 | yarn create react-app my-app --template unicorn 27 | ``` 28 | 29 | ## In this template 30 | 31 | - [craco](https://github.com/gsoft-inc/craco) 32 | - [redux-toolkit](https://github.com/reduxjs/redux-toolkit) 33 | - [react-redux](https://github.com/reduxjs/react-redux) 34 | - [react-router](https://github.com/ReactTraining/react-router) 35 | 36 | ## Support 37 | 38 | - Support VSCode Integration 39 | - Support reset.css 40 | - Support absolute path 41 | - Customize config with craco 42 | - Customize eslint config > [link](https://create-react-app.dev/docs/advanced-configuration) 43 | 44 | ## Show your support 45 | 46 | Give a ⭐️ if this project helped you! 47 | 48 |
49 | 50 | Written by @Jbee 51 | 52 |
53 | -------------------------------------------------------------------------------- /template/craco.config.js: -------------------------------------------------------------------------------- 1 | const path = require('path') 2 | const resolve = arg => path.resolve(__dirname, arg) 3 | 4 | module.exports = function() { 5 | return { 6 | babel: { 7 | plugins: [ 8 | [ 9 | 'emotion', 10 | { 11 | labelFormat: '[filename]--[local]', 12 | }, 13 | ], 14 | ], 15 | }, 16 | webpack: { 17 | alias: { 18 | '@': resolve('src'), 19 | }, 20 | }, 21 | jest: { 22 | configure: { 23 | moduleNameMapper: { 24 | '^@/(.*)$': '/src/$1', 25 | }, 26 | }, 27 | }, 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /template/gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/articles/ignoring-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | /.pnp 6 | .pnp.js 7 | 8 | # testing 9 | /coverage 10 | 11 | # production 12 | /build 13 | 14 | # misc 15 | .DS_Store 16 | .env.local 17 | .env.development.local 18 | .env.test.local 19 | .env.production.local 20 | 21 | npm-debug.log* 22 | yarn-debug.log* 23 | yarn-error.log* 24 | -------------------------------------------------------------------------------- /template/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/jbee37142/cra-template-unicorn/f467b79652f038b2dbb492c13823677f582d2c0c/template/public/favicon.ico -------------------------------------------------------------------------------- /template/public/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 12 | 13 | 14 | 15 | React Unicorn Template 16 | 17 | 18 | 19 |
20 | 21 | 22 | -------------------------------------------------------------------------------- /template/public/logo192.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/jbee37142/cra-template-unicorn/f467b79652f038b2dbb492c13823677f582d2c0c/template/public/logo192.png -------------------------------------------------------------------------------- /template/public/logo512.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/jbee37142/cra-template-unicorn/f467b79652f038b2dbb492c13823677f582d2c0c/template/public/logo512.png -------------------------------------------------------------------------------- /template/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | }, 10 | { 11 | "src": "logo192.png", 12 | "type": "image/png", 13 | "sizes": "192x192" 14 | }, 15 | { 16 | "src": "logo512.png", 17 | "type": "image/png", 18 | "sizes": "512x512" 19 | } 20 | ], 21 | "start_url": ".", 22 | "display": "standalone", 23 | "theme_color": "#000000", 24 | "background_color": "#ffffff" 25 | } 26 | -------------------------------------------------------------------------------- /template/public/reset.css: -------------------------------------------------------------------------------- 1 | /* http://meyerweb.com/eric/tools/css/reset/ 2 | v2.0-modified | 20110126 3 | License: none (public domain) 4 | */ 5 | 6 | html, 7 | body, 8 | div, 9 | span, 10 | applet, 11 | object, 12 | iframe, 13 | h1, 14 | h2, 15 | h3, 16 | h4, 17 | h5, 18 | h6, 19 | p, 20 | blockquote, 21 | pre, 22 | a, 23 | abbr, 24 | acronym, 25 | address, 26 | big, 27 | cite, 28 | code, 29 | del, 30 | dfn, 31 | em, 32 | img, 33 | ins, 34 | kbd, 35 | q, 36 | s, 37 | samp, 38 | small, 39 | strike, 40 | strong, 41 | sub, 42 | sup, 43 | tt, 44 | var, 45 | b, 46 | u, 47 | i, 48 | center, 49 | dl, 50 | dt, 51 | dd, 52 | ol, 53 | ul, 54 | li, 55 | fieldset, 56 | form, 57 | label, 58 | legend, 59 | table, 60 | caption, 61 | tbody, 62 | tfoot, 63 | thead, 64 | tr, 65 | th, 66 | td, 67 | article, 68 | aside, 69 | canvas, 70 | details, 71 | embed, 72 | figure, 73 | figcaption, 74 | footer, 75 | header, 76 | hgroup, 77 | menu, 78 | nav, 79 | output, 80 | ruby, 81 | section, 82 | summary, 83 | time, 84 | mark, 85 | audio, 86 | video { 87 | margin: 0; 88 | padding: 0; 89 | border: 0; 90 | font-size: 100%; 91 | font: inherit; 92 | vertical-align: baseline; 93 | } 94 | 95 | /* make sure to set some focus styles for accessibility */ 96 | :focus { 97 | outline: 0; 98 | } 99 | 100 | /* HTML5 display-role reset for older browsers */ 101 | article, 102 | aside, 103 | details, 104 | figcaption, 105 | figure, 106 | footer, 107 | header, 108 | hgroup, 109 | menu, 110 | nav, 111 | section { 112 | display: block; 113 | } 114 | 115 | body { 116 | line-height: 1; 117 | } 118 | 119 | ol, 120 | ul { 121 | list-style: none; 122 | } 123 | 124 | blockquote, 125 | q { 126 | quotes: none; 127 | } 128 | 129 | blockquote:before, 130 | blockquote:after, 131 | q:before, 132 | q:after { 133 | content: ""; 134 | content: none; 135 | } 136 | 137 | table { 138 | border-collapse: collapse; 139 | border-spacing: 0; 140 | } 141 | 142 | input[type="search"]::-webkit-search-cancel-button, 143 | input[type="search"]::-webkit-search-decoration, 144 | input[type="search"]::-webkit-search-results-button, 145 | input[type="search"]::-webkit-search-results-decoration { 146 | -webkit-appearance: none; 147 | -moz-appearance: none; 148 | } 149 | 150 | input[type="search"] { 151 | -webkit-appearance: none; 152 | -moz-appearance: none; 153 | -webkit-box-sizing: content-box; 154 | -moz-box-sizing: content-box; 155 | box-sizing: content-box; 156 | } 157 | 158 | textarea { 159 | overflow: auto; 160 | vertical-align: top; 161 | resize: vertical; 162 | } 163 | 164 | /** 165 | * Correct `inline-block` display not defined in IE 6/7/8/9 and Firefox 3. 166 | */ 167 | 168 | audio, 169 | canvas, 170 | video { 171 | display: inline-block; 172 | *display: inline; 173 | *zoom: 1; 174 | max-width: 100%; 175 | } 176 | 177 | /** 178 | * Prevent modern browsers from displaying `audio` without controls. 179 | * Remove excess height in iOS 5 devices. 180 | */ 181 | 182 | audio:not([controls]) { 183 | display: none; 184 | height: 0; 185 | } 186 | 187 | /** 188 | * Address styling not present in IE 7/8/9, Firefox 3, and Safari 4. 189 | * Known issue: no IE 6 support. 190 | */ 191 | 192 | [hidden] { 193 | display: none; 194 | } 195 | 196 | /** 197 | * 1. Correct text resizing oddly in IE 6/7 when body `font-size` is set using 198 | * `em` units. 199 | * 2. Prevent iOS text size adjust after orientation change, without disabling 200 | * user zoom. 201 | */ 202 | 203 | html { 204 | font-size: 100%; /* 1 */ 205 | -webkit-text-size-adjust: 100%; /* 2 */ 206 | -ms-text-size-adjust: 100%; /* 2 */ 207 | } 208 | 209 | /** 210 | * Address `outline` inconsistency between Chrome and other browsers. 211 | */ 212 | 213 | a:focus { 214 | outline: thin dotted; 215 | } 216 | 217 | /** 218 | * Improve readability when focused and also mouse hovered in all browsers. 219 | */ 220 | 221 | a:active, 222 | a:hover { 223 | outline: 0; 224 | } 225 | 226 | /** 227 | * 1. Remove border when inside `a` element in IE 6/7/8/9 and Firefox 3. 228 | * 2. Improve image quality when scaled in IE 7. 229 | */ 230 | 231 | img { 232 | border: 0; /* 1 */ 233 | -ms-interpolation-mode: bicubic; /* 2 */ 234 | } 235 | 236 | /** 237 | * Address margin not present in IE 6/7/8/9, Safari 5, and Opera 11. 238 | */ 239 | 240 | figure { 241 | margin: 0; 242 | } 243 | 244 | /** 245 | * Correct margin displayed oddly in IE 6/7. 246 | */ 247 | 248 | form { 249 | margin: 0; 250 | } 251 | 252 | /** 253 | * Define consistent border, margin, and padding. 254 | */ 255 | 256 | fieldset { 257 | border: 1px solid #c0c0c0; 258 | margin: 0 2px; 259 | padding: 0.35em 0.625em 0.75em; 260 | } 261 | 262 | /** 263 | * 1. Correct color not being inherited in IE 6/7/8/9. 264 | * 2. Correct text not wrapping in Firefox 3. 265 | * 3. Correct alignment displayed oddly in IE 6/7. 266 | */ 267 | 268 | legend { 269 | border: 0; /* 1 */ 270 | padding: 0; 271 | white-space: normal; /* 2 */ 272 | *margin-left: -7px; /* 3 */ 273 | } 274 | 275 | /** 276 | * 1. Correct font size not being inherited in all browsers. 277 | * 2. Address margins set differently in IE 6/7, Firefox 3+, Safari 5, 278 | * and Chrome. 279 | * 3. Improve appearance and consistency in all browsers. 280 | */ 281 | 282 | button, 283 | input, 284 | select, 285 | textarea { 286 | font-size: 100%; /* 1 */ 287 | margin: 0; /* 2 */ 288 | vertical-align: baseline; /* 3 */ 289 | *vertical-align: middle; /* 3 */ 290 | } 291 | 292 | /** 293 | * Address Firefox 3+ setting `line-height` on `input` using `!important` in 294 | * the UA stylesheet. 295 | */ 296 | 297 | button, 298 | input { 299 | line-height: normal; 300 | } 301 | 302 | /** 303 | * Address inconsistent `text-transform` inheritance for `button` and `select`. 304 | * All other form control elements do not inherit `text-transform` values. 305 | * Correct `button` style inheritance in Chrome, Safari 5+, and IE 6+. 306 | * Correct `select` style inheritance in Firefox 4+ and Opera. 307 | */ 308 | 309 | button, 310 | select { 311 | text-transform: none; 312 | } 313 | 314 | /** 315 | * 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` 316 | * and `video` controls. 317 | * 2. Correct inability to style clickable `input` types in iOS. 318 | * 3. Improve usability and consistency of cursor style between image-type 319 | * `input` and others. 320 | * 4. Remove inner spacing in IE 7 without affecting normal text inputs. 321 | * Known issue: inner spacing remains in IE 6. 322 | */ 323 | 324 | button, 325 | html input[type="button"], /* 1 */ 326 | input[type="reset"], 327 | input[type="submit"] { 328 | -webkit-appearance: button; /* 2 */ 329 | cursor: pointer; /* 3 */ 330 | *overflow: visible; /* 4 */ 331 | } 332 | 333 | /** 334 | * Re-set default cursor for disabled elements. 335 | */ 336 | 337 | button[disabled], 338 | html input[disabled] { 339 | cursor: default; 340 | } 341 | 342 | /** 343 | * 1. Address box sizing set to content-box in IE 8/9. 344 | * 2. Remove excess padding in IE 8/9. 345 | * 3. Remove excess padding in IE 7. 346 | * Known issue: excess padding remains in IE 6. 347 | */ 348 | 349 | input[type="checkbox"], 350 | input[type="radio"] { 351 | box-sizing: border-box; /* 1 */ 352 | padding: 0; /* 2 */ 353 | *height: 13px; /* 3 */ 354 | *width: 13px; /* 3 */ 355 | } 356 | 357 | /** 358 | * 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 359 | * 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome 360 | * (include `-moz` to future-proof). 361 | */ 362 | 363 | input[type="search"] { 364 | -webkit-appearance: textfield; /* 1 */ 365 | -moz-box-sizing: content-box; 366 | -webkit-box-sizing: content-box; /* 2 */ 367 | box-sizing: content-box; 368 | } 369 | 370 | /** 371 | * Remove inner padding and search cancel button in Safari 5 and Chrome 372 | * on OS X. 373 | */ 374 | 375 | input[type="search"]::-webkit-search-cancel-button, 376 | input[type="search"]::-webkit-search-decoration { 377 | -webkit-appearance: none; 378 | } 379 | 380 | /** 381 | * Remove inner padding and border in Firefox 3+. 382 | */ 383 | 384 | button::-moz-focus-inner, 385 | input::-moz-focus-inner { 386 | border: 0; 387 | padding: 0; 388 | } 389 | 390 | /** 391 | * 1. Remove default vertical scrollbar in IE 6/7/8/9. 392 | * 2. Improve readability and alignment in all browsers. 393 | */ 394 | 395 | textarea { 396 | overflow: auto; /* 1 */ 397 | vertical-align: top; /* 2 */ 398 | } 399 | 400 | /** 401 | * Remove most spacing between table cells. 402 | */ 403 | 404 | table { 405 | border-collapse: collapse; 406 | border-spacing: 0; 407 | } 408 | 409 | html, 410 | button, 411 | input, 412 | select, 413 | textarea { 414 | color: #222; 415 | } 416 | 417 | ::-moz-selection { 418 | background: #b3d4fc; 419 | text-shadow: none; 420 | } 421 | 422 | ::selection { 423 | background: #b3d4fc; 424 | text-shadow: none; 425 | } 426 | 427 | img { 428 | vertical-align: middle; 429 | } 430 | 431 | fieldset { 432 | border: 0; 433 | margin: 0; 434 | padding: 0; 435 | } 436 | 437 | textarea { 438 | resize: vertical; 439 | } 440 | 441 | .chromeframe { 442 | margin: 0.2em 0; 443 | background: #ccc; 444 | color: #000; 445 | padding: 0.2em 0; 446 | } 447 | -------------------------------------------------------------------------------- /template/public/robots.txt: -------------------------------------------------------------------------------- 1 | # https://www.robotstxt.org/robotstxt.html 2 | User-agent: * 3 | -------------------------------------------------------------------------------- /template/src/components/App.test.tsx: -------------------------------------------------------------------------------- 1 | import { render } from '@testing-library/react' 2 | import React from 'react' 3 | 4 | import App from './App' 5 | 6 | test('renders learn react link', () => { 7 | const { getByText } = render() 8 | const linkElement = getByText(/learn react/i) 9 | expect(linkElement).toBeInTheDocument() 10 | }) 11 | -------------------------------------------------------------------------------- /template/src/components/App.tsx: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | 3 | export default () => { 4 | return ( 5 |

6 | 11 | cra-template-unicorn 12 | 13 |

14 | ) 15 | } 16 | -------------------------------------------------------------------------------- /template/src/components/shared/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/jbee37142/cra-template-unicorn/f467b79652f038b2dbb492c13823677f582d2c0c/template/src/components/shared/.gitkeep -------------------------------------------------------------------------------- /template/src/features/index.ts: -------------------------------------------------------------------------------- 1 | import { combineReducers } from '@reduxjs/toolkit' 2 | import { configureStore } from '@reduxjs/toolkit' 3 | 4 | const rootReducer = combineReducers({}) 5 | 6 | const store = configureStore({ reducer: rootReducer }) 7 | 8 | export type RootState = ReturnType 9 | export default store 10 | -------------------------------------------------------------------------------- /template/src/index.tsx: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import ReactDOM from 'react-dom' 3 | import { Provider } from 'react-redux' 4 | import { Router } from 'react-router-dom' 5 | 6 | import App from '@/components/App' 7 | import store from '@/features' 8 | import history from '@/utils/history' 9 | 10 | ReactDOM.render( 11 | 12 | 13 | 14 | 15 | , 16 | document.getElementById('root'), 17 | ) 18 | -------------------------------------------------------------------------------- /template/src/react-app-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /template/src/setupTests.ts: -------------------------------------------------------------------------------- 1 | // jest-dom adds custom jest matchers for asserting on DOM nodes. 2 | // allows you to do things like: 3 | // expect(element).toHaveTextContent(/react/i) 4 | // learn more: https://github.com/testing-library/jest-dom 5 | import '@testing-library/jest-dom/extend-expect' 6 | -------------------------------------------------------------------------------- /template/src/utils/history.ts: -------------------------------------------------------------------------------- 1 | import { createBrowserHistory } from 'history' 2 | 3 | export default createBrowserHistory() 4 | -------------------------------------------------------------------------------- /template/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "./tsconfig.paths.json", 3 | "compilerOptions": { 4 | "target": "es5", 5 | "lib": [ 6 | "dom", 7 | "dom.iterable", 8 | "esnext" 9 | ], 10 | "allowJs": true, 11 | "skipLibCheck": true, 12 | "esModuleInterop": true, 13 | "allowSyntheticDefaultImports": true, 14 | "strict": true, 15 | "forceConsistentCasingInFileNames": true, 16 | "module": "esnext", 17 | "moduleResolution": "node", 18 | "resolveJsonModule": true, 19 | "isolatedModules": true, 20 | "noEmit": true, 21 | "jsx": "react" 22 | }, 23 | "include": [ 24 | "src" 25 | ] 26 | } 27 | -------------------------------------------------------------------------------- /template/tsconfig.paths.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "baseUrl": "./", 4 | "paths": { 5 | "@/*": ["src/*"] 6 | } 7 | } 8 | } 9 | --------------------------------------------------------------------------------