15
votes

Comment configurer des chemins absolus pour les importations dans les applications React Native basées sur TypeScript?

Afin d'éviter les importations relatives de style «../../../../» dans une application React Native basée sur TypeScript, je voudrais configurer l'application afin que je puisse utiliser des importations absolues à la place.

Il est important que la configuration prenne également en charge les tests unitaires Jest.

J'ai créé l'application à l'aide de npx react-native init MyTestApp --template typescript

Version native de React: 0.60.5

Quelle est la configuration exacte dont j'aurais besoin pour y parvenir?


0 commentaires

5 Réponses :


17
votes

Sommaire:

Le package npm babel-plugin-module-resolver est nécessaire, ainsi qu'une configuration dans tsconfig.json et babel.config.js


Pas à pas:

  1. npm install babel-plugin-module-resolver (ou yarn add babel-plugin-module-resolver )

  2. tsconfig.json : Ajoutez "baseUrl": "." à compilerOptions

  3. babel.config.js : ajoutez une clé nommée plugins avec la valeur suivante:

module.exports = {
  presets: ['module:metro-react-native-babel-preset'],
  plugins: [
    [
      'module-resolver',
      {
        extensions: [
          '.js',
          '.jsx',
          '.ts',
          '.tsx',
          '.android.js',
          '.android.tsx',
          '.ios.js',
          '.ios.tsx'
        ],
        root: ['.']
      }
    ]
  ]
};


Configuration complète:

tsconfig.json :

{
  "compilerOptions": {
    "allowJs": true,
    "allowSyntheticDefaultImports": true,
    "esModuleInterop": true,
    "isolatedModules": true,
    "jsx": "react",
    "lib": ["es6"],
    "moduleResolution": "node",
    "noEmit": true,
    "strict": true,
    "target": "esnext",
    "baseUrl": "."
  },
  "exclude": ["node_modules", "babel.config.js", "metro.config.js", "jest.config.js"]
}

babel.config.js :

[
    [
      'module-resolver',
      {
        extensions: [
          '.js',
          '.jsx',
          '.ts',
          '.tsx',
          '.android.js',
          '.android.tsx',
          '.ios.js',
          '.ios.tsx'
        ],
        root: ['.']
      }
    ]
  ]

Ceci est pour un nouveau projet propre créé à l'aide de npx react-native init MyTestApp --template typescript sur React Native version 0.60.5


1 commentaires

babel-plugin-module-resolver doit être installé dans devDependencies



17
votes

Exigence
{
  "compilerOptions": {
    "allowJs": true,
    "allowSyntheticDefaultImports": true,
    "esModuleInterop": true,
    "isolatedModules": true,
    "jsx": "react",
    "lib": ["es2015", "es2015.promise", "es2016.array.include", "dom"],
    "strict": true,
    "moduleResolution": "node",
    "baseUrl": "./",
    "paths": {
      "@cuteapp/*": ["app/*/index", "app/*"]
    },
    "noEmit": true,
    "resolveJsonModule": true,
    "target": "esnext",
    "types": ["jest"]
  },
  "exclude": ["node_modules", "babel.config.js", "metro.config.js"]
}

Comment

  1. Ajouter ce package de plugin Babel
module.exports = {
  presets: ['module:metro-react-native-babel-preset'],
  plugins: [
    [
      require.resolve('babel-plugin-module-resolver'),
      {
        cwd: 'babelrc',
        extensions: ['.ts', '.tsx', '.js', '.ios.js', '.android.js'],
        alias: {
          '@cuteapp': './app'
        }
      }
    ],
    'jest-hoist'
  ]
};
  1. Mon babel.config.js
yarn add --dev babel-plugin-module-resolver
  1. Mon tsconfig.json
// Meh
import config from '../../../../../../../config';

// Awesome!
import config from '@cuteapp/config';
  1. C'est ça.

2 commentaires

Une petite chose (mais potentiellement déroutante) - c'est babel-config-js (pas json )


la clé tsconfig.json jsx doit également être react-native selon la question.



3
votes

Pour tous ceux qui utilisent TypeScript et souhaitent simplement utiliser l'importation avec des chemins absolus sans alias.

En supposant que tous vos dossiers de code sont à l'intérieur de src .

Insérez "baseUrl": "src" dans l'objet compilerOptions dans tsconfig.json .

Vous pouvez désormais utiliser des chemins absolus dans les importations.


1 commentaires

Cela ne fera que faire fonctionner la vérification de type, cela n'aidera pas à la compilation



-2
votes

Vous pouvez le résoudre en 5 étapes simples sans éjecter :

Étape 1 : Ajout de react-app-rewired dans vos devDependencies .

yarn add -D react-app-rewired npm intall react-app-rewired --save-dev ou npm intall react-app-rewired --save-dev

Étape 2 : Après l'installation, vous pourrez modifier les scripts ReactsJS par défaut de package.json en:

const path = require('path');

module.exports = function override(config) {
  config.resolve = {
    ...config.resolve,
    alias: {
      ...config.alias,
      'services': path.resolve(__dirname, 'src/shared/services'),
      'interfaces': path.resolve(__dirname, 'src/shared/interfaces')
    },
  };

  return config;
};

Étape 3 : crée un nouveau fichier appelé tsconfig.paths.json sur le chemin racine, avec un contenu comme:

{
  "extends": "./tsconfig.paths.json",
  ...//rest of file infos compilerOptions, include... whatever
}

Astuce 1 : vous pouvez choisir le chemin que vous souhaitez utiliser, comme: @services, @interface, @src, ~, @, etc en changeant simplement les clés à l'intérieur de "paths": {}

La même chose s'applique à sa valeur: ["src/shared/services/ "], ["src/shared/interfaces/ "], ["src/*"] , utilisez le chemin relatif ici.

Étape 4 : Dans tsconfig.json , avant "compilerOptions" vous devez étendre le tsconfig.paths.json vous venez de créer.

Comme ça:

{
  "compilerOptions": {
    "baseUrl": ".",
    "paths": {
      "services/*": ["./src/shared/services/*"],
      "interfaces/*": ["./src/shared/interfaces/*"]
    }
  }
}

Étape 5 : crée un nouveau fichier config-overrides.js , en y ajoutant votre alias et les chemins relatifs:

"scripts": {  
  "start": "react-app-rewired start",  
  "build": "react-app-rewired build",  
  "test": "react-app-rewired test",  
  "eject": "react-app-rewired eject" 
}

Astuce 2 : Si vous utilisez eslint , n'oubliez pas d'avoir un fichier .eslintignore et ajoutez config-overrides.js y config-overrides.js .

Redémarrez votre IDE ou votre éditeur de texte, dans mon cas VSCode.

C'est fait ! . Maintenant, lancez simplement yarn start ou npm run start


0 commentaires

0
votes

Toutes les autres réponses n'ont pas fonctionné pour moi avec un projet React Native + Typescript fraîchement créé.

Ce qui a fonctionné pour moi a été de définir à la fois baseUrl et les paths dans tsconfig.json :

{
    "baseUrl": ".",
    "paths": {
      "NAME_IN_PACKAGE_JSON/*": ["./*"]
    }
}

Remplacez NAME_IN_PACKAGE_JSON par le champ de nom de votre package.json . Par exemple, si le champ de nom est myapp vous pouvez faire:

import HomeScreen from "myapp/screens/HomeScreen";


1 commentaires

Lorsque j'essaye de définir des "paths" , j'obtiens ceci au moment de la construction: The following changes are being made to your tsconfig.json file: - compilerOptions.paths must not be set (aliased imports are not supported) , mais apparemment juste le "baseUrl" paramètre "baseUrl" suffit maintenant. Au moins pour moi, cela fonctionne bien.