@types/fbt
Type definitions for the fbt to your project.
Installation
npm install --save @types/fbt
Using
Typescript 4.2+
TypeScript 4.2 supports XML namespaces in JSX (#11833) and you can easily use <ftb:param>{...}</ftb:param> without any issues:
Example:
// App.tsx
import React from "react";
import fbt from "fbt";
const name = "Mary";
function App() {
return (
<fbt desc="param example">
Hello,
<fbt:param name="name">{name}</fbt:param>.
</fbt>
);
}
Typescript 3.9 − 4.2
Older versions of typescript which don't have support XML namespaces in JSX, will throw lots of errors:
<fbt:param name="name">
{name}
</fbt:param>
Error:(6, 28) TS1003: Identifier expected.
Error:(6, 64) TS1005: '>' expected.
Error:(6, 70) TS1005: ',' expected.
Error:(7, 3) TS1109: Expression expected.
Error:(8, 1) TS1109: Expression expected.
So, one way it to replace xml syntax with camelcase variants of components: babel-plugin-fbt/FbtUtil.js#L119-L124
<fbt:enum/> <FbtEnum/>
<fbt:param/> <FbtParam/>
<fbt:plural/> <FbtPlural/>
<fbt:pronoun/> <FbtPronoun/>
<fbt:name/> <FbtName/>
<fbt:same-param/> <FbtSameParam/>
Example:
// App.tsx
import React from "react";
import { fbt, FbtParam } from "fbt";
const name = "Mary";
function App() {
return (
<fbt desc="param example">
Hello,
<FbtParam name="name">{name}</FbtParam>.
</fbt>
);
}
Known issues
@babel/preset-typescript will remove fbt import as unused that bring to next error:
Error: App.tsx: Line 8 Column 5: fbt is not bound. Did you forget to require('fbt')?
What happened under hood:
- In JSX
<fbt/>=> in just a function callReact.createElement("fbt") - So, when
@babel/plugin-transform-typescriptcheck all imports and find that afbtvariable never used => remove import (see: babel-plugin-transform-typescript/src/index.ts) - After that
babel-plugin-fbttry transform all<fbt/>elements tofbt._(...)and as import was removed on previous step it case an error above
How fix this problem:
- Change removing imports behavior
When enable onlyRemoveTypeImports the transform will only remove type-only imports instead of removing all unused imports
// babel.config.js
module.exports = {
presets: [["@babel/preset-typescript", { onlyRemoveTypeImports: true }]],
plugins,
};
- Modify babel plugin
Using a patch-package you can add logic to ignore removing fbt import
-
Install
yarn add -D patch-package -
Open file
./node_modules/@babel/plugin-transform-typescript/lib/index.js -
Find
isImportTypeOnlyfunction and add the next lines beforeif(binding.identifier.name !== pragmaImportName ...block+if (binding.identifier.name === 'fbt') { + return false; +} if (binding.identifier.name !== pragmaImportName && binding.identifier.name !== pragmaFragImportName) { return true; } -
Create a patch
npx patch-package @babel/plugin-transform-typescript -
Add
postinstallscript inpackage.json"scripts": { + "postinstall": "patch-package" } -
Commit changed & new files