Looks like optional chaining has landed. Here's an example
What I can't figure out is how to get TS to compile it properly. I'm not getting any syntax errors in my project, but this:
let imageFileId = (await db.query(sql`select id from image_files where sha256=${sha256}`))[0]?.id;
Is being output as:
let imageFileId = (await db.query(mysql3_1.sql `select id from image_files where sha256=${sha256}`))[0]?.id;
Which won't run until we get native support in Node.
Here's my tsconfig:
{
"compilerOptions": {
"strict": true,
"importHelpers": false,
"inlineSources": true,
"noEmitOnError": true,
"pretty": true,
"module": "commonjs",
"noImplicitAny": true,
"suppressImplicitAnyIndexErrors": false,
"removeComments": false,
"preserveConstEnums": false,
"sourceMap": true,
"lib": ["es2018"],
"skipLibCheck": false,
"outDir": "dist",
"target": "esnext",
"declaration": false,
"resolveJsonModule": true,
"esModuleInterop": false,
"moduleResolution": "node",
"allowSyntheticDefaultImports": true,
"baseUrl": ".",
"paths": {
"*": ["src/*"]
},
"noEmit": false
},
"files": [
"src/index"
],
"include": [
"src/**/*.d.ts"
]
}
Is there some other option I need to enable to compile the ?.
operator?
Please note I'm not using Babel and I don't want to bring it into the picture.
In TypeScript, optional chaining is defined as the ability to immediately stop running an expression if a part of it evaluates to either null or undefined .
You must tell TypeScript if a property is optional. First, if you don't tell TypeScript that a property is optional, it will expect it to be set. Adding ? to the property name on a type, interface, or class definition will mark that property as optional.
You can use optional chaining when attempting to call a method which may not exist. This can be helpful, for example, when using an API in which a method might be unavailable, either due to the age of the implementation or because of a feature which isn't available on the user's device.
To enable optional chaining, you need to install a package. At the time of writing, optional chaining is not natively supported in Javascript, it is a new feature introduced in ES2020. Until it is fully adopted we can get all the optional goodness by installing a package!
The problem is you are targeting esnext
this will tell the compiler to output all language features as is without any transpilation. Set the language to es2020 (or below) and ?.
and ??
will get transpiled to compatible code:
(async function () {
let imageFileId = (await db.query(sql`select id from image_files where sha256=${sha256}`))[0]?.id;
})()
Playground Link
There is no fine-grained control over which language features get transpiled and which don't do you have to pick a version as a whole unfortunately,
Well, I didn't want to use Babel because then I'd have to figure out how to replace ts-node
. There's a bunch of outdated docs out there referring to old Babel packages, but these instructions should work as of Nov 2019:
Add a .babelrc
file:
{
"presets": [
["@babel/preset-env",{"targets": {"node": "current"}}],
"@babel/preset-typescript"
],
"plugins": [
"@babel/plugin-syntax-bigint"
]
}
Add these deps:
"devDependencies": {
"@babel/cli": "^7.7.0",
"@babel/core": "^7.7.0",
"@babel/node": "^7.7.0",
"@babel/plugin-syntax-bigint": "^7.4.4",
"@babel/preset-env": "^7.7.1",
"@babel/preset-typescript": "^7.7.0",
"@types/node": "^12.7.5",
"typescript": "^3.7.2"
}
Execute your code with:
node_modules/.bin/babel-node --extensions ".ts" src/index.ts
The --extensions ".ts"
is very important, even though you're explicitly trying to execute a .ts file, it won't transpile it w/out that.
I like to use GNU Make instead of package.json scripts:
MAKEFLAGS += --no-builtin-rules
.SUFFIXES:
NM := node_modules/.bin
.PHONY: build start dev clean test publish
## commands
########################################
__default:
$(error Please specify a target)
build: build-types build-js dist/package.json
build-types: node_modules/.yarn-integrity
$(NM)/tsc --emitDeclarationOnly
build-js: node_modules/.yarn-integrity
$(NM)/babel src --out-dir dist --extensions ".ts" --source-maps inline
run: node_modules/.yarn-integrity
$(NM)/babel-node --extensions ".ts" src/index.ts
check: node_modules/.yarn-integrity
$(NM)/tsc --noEmit
dist:
mkdir -p $@
clean:
rm -rf node_modules dist yarn-error.log
dist/package.json: package.json | dist
jq 'del(.private, .devDependencies, .scripts, .eslintConfig, .babel)' $< > $@
## files
########################################
node_modules/.yarn-integrity: yarn.lock
@yarn install --frozen-lockfile --production=false --check-files
@touch -mr $@ $<
yarn.lock: package.json
@yarn check --integrity
@touch -mr $@ $<
Or just copy from Microsoft's TypeScript Babel Starter.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With