diff --git a/.eslintrc.cjs b/.eslintrc.cjs new file mode 100644 index 0000000000..b51149cf57 --- /dev/null +++ b/.eslintrc.cjs @@ -0,0 +1,108 @@ +module.exports = { + env: { + browser: true, + es2024: true, + }, + extends: [ + 'plugin:react/recommended', + "plugin:react-hooks/recommended", + 'airbnb-typescript', + 'plugin:@typescript-eslint/eslint-recommended', + 'plugin:@typescript-eslint/recommended', + 'plugin:prettier/recommended', + 'plugin:cypress/recommended', + ], + overrides: [ + { + 'files': ['**/*.spec.jsx'], + 'rules': { + 'react/jsx-filename-extension': ['off'], + } + } + ], + parser: '@typescript-eslint/parser', + parserOptions: { + ecmaFeatures: { + jsx: true, + }, + ecmaVersion: 12, + project: './tsconfig.json', + sourceType: 'module', + }, + plugins: [ + 'jsx-a11y', + 'import', + 'react-hooks', + '@typescript-eslint', + 'prettier' + ], + rules: { + // JS + 'semi': 'off', + '@typescript-eslint/semi': ['error', 'always'], + 'prefer-const': 2, + curly: [2, 'all'], + 'max-len': ['error', { + ignoreTemplateLiterals: true, + ignoreComments: true, + }], + 'no-redeclare': [2, { builtinGlobals: true }], + 'no-console': 2, + 'operator-linebreak': 0, + 'brace-style': [2, '1tbs'], + 'arrow-body-style': 0, + 'arrow-parens': 0, + 'no-param-reassign': [2, { props: true }], + 'padding-line-between-statements': [ + 2, + { blankLine: 'always', prev: '*', next: 'return' }, + { blankLine: 'always', prev: ['const', 'let', 'var'], next: '*' }, + { blankLine: 'any', prev: ['const', 'let', 'var'], next: ['const', 'let', 'var'] }, + { blankLine: 'always', prev: 'directive', next: '*' }, + { blankLine: 'always', prev: 'block-like', next: '*' }, + ], + 'implicit-arrow-linebreak:': 0, + + // React + 'react/prop-types': 0, + 'react/require-default-props': 0, + 'import/prefer-default-export': 0, + 'standard/no-callback-literal': 0, + 'react/jsx-filename-extension': [1, { extensions: ['.tsx'] }], + 'react/destructuring-assignment': 0, + 'react/jsx-props-no-spreading': 0, + 'react/state-in-constructor': [2, 'never'], + 'react-hooks/rules-of-hooks': 2, + 'jsx-a11y/label-has-associated-control': ["error", { + assert: "either", + }], + 'jsx-a11y/label-has-for': [2, { + components: ['Label'], + required: { + some: ['id', 'nesting'], + }, + allowChildren: true, + }], + 'react/jsx-uses-react': 'off', + 'react/react-in-jsx-scope': 'off', + + // Typescript + '@typescript-eslint/explicit-function-return-type': 'off', + '@typescript-eslint/explicit-module-boundary-types': 'off', + '@typescript-eslint/no-unused-vars': ['error'], + '@typescript-eslint/indent': ['error', 2], + '@typescript-eslint/ban-types': ['error', { + extendDefaults: true, + types: { + '{}': false, + }, + }, + ], + }, + ignorePatterns: ['dist', '.eslintrc.cjs', 'vite.config.ts', 'src/vite-env.d.ts', 'cypress'], + settings: { + react: { + version: 'detect', + }, + }, +}; diff --git a/.eslintrc.js b/.eslintrc.js deleted file mode 100644 index aeb79e7e23..0000000000 --- a/.eslintrc.js +++ /dev/null @@ -1,12 +0,0 @@ -module.exports = { - extends: ['@mate-academy/eslint-config-react-typescript', 'plugin:cypress/recommended'], - rules: { - 'max-len': ['error', { - ignoreTemplateLiterals: true, - ignoreComments: true, - }], - 'jsx-a11y/label-has-associated-control': ["error", { - assert: "either", - }], - }, -}; diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 2b04d50bb5..6cfdef607b 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -11,7 +11,7 @@ jobs: strategy: matrix: - node-version: [14.x] + node-version: [20.x] steps: - uses: actions/checkout@v2 diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 162d82ee42..2e850d6de9 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -11,7 +11,7 @@ jobs: strategy: matrix: - node-version: [14.x] + node-version: [20.x] steps: - uses: actions/checkout@v2 @@ -23,7 +23,7 @@ jobs: - run: npm test -- -l - name: Upload tests report(cypress mochaawesome merged HTML report) if: ${{ always() }} - uses: actions/upload-artifact@v2 + uses: actions/upload-artifact@v4 with: name: report path: reports diff --git a/.prettierignore b/.prettierignore new file mode 100644 index 0000000000..febbb5c964 --- /dev/null +++ b/.prettierignore @@ -0,0 +1,2 @@ +/node_modules +/build diff --git a/.prettierrc b/.prettierrc new file mode 100644 index 0000000000..49b905d690 --- /dev/null +++ b/.prettierrc @@ -0,0 +1,11 @@ +{ + "arrowParens": "avoid", + "singleQuote": true, + "tabWidth": 2, + "trailingComma": "all", + "jsxSingleQuote": false, + "printWidth": 80, + "semi": true, + "bracketSpacing": true, + "bracketSameLine": false +} diff --git a/README.md b/README.md index 074475e44f..98eb0bd1c0 100644 --- a/README.md +++ b/README.md @@ -1,120 +1,143 @@ -# React Phone catalog -- If you work alone follow the [React task guideline](https://github.com/mate-academy/react_task-guideline#react-tasks-guideline) -- If you work in a team follow the [Work in a team guideline](https://github.com/mate-academy/react_task-guideline/blob/master/team-flow.md#how-to-work-in-a-team) - -## Description -Implement Products catalog following [this design](https://www.figma.com/file/uEetgWenSRxk9jgiym6Yzp/Phone-catalog-redesign?node-id=1%3A2). - -Use [products](https://mate-academy.github.io/react_phone-catalog/api/products.json) -and [product details](https://mate-academy.github.io/react_phone-catalog/api/products/dell-streak-7.json) -tо fetch data (use actual `productId` as a last part of the URL before `.json`). - -If you want to change any API data for the phones you can update the files in the `/public/api` folder, and use you project link as a `BASE_API_URL`. - -Store the Cart in the `localStorage` - -## Tasks -- Create `pages`, `components` and `helpers` folders to structure your app -- Use `scss` files per component -- Use component names as BEM block names with all the other BEM rules applied - -### App -1. Add `
` with links to all the pages - - The `Logo` and the `Nav` are aligned left - - The `Favorites` and the `Cart` are aligned right -1. Use `NavLink` to highlight current page in `Header` -1. Add `