Next.js と TypeScript で、関数の引数を無視するパラメータ`_`の使い所

TwitterFacebookHatena

TL;DR

このページでは、引数を無視するパラメータ_の実装方法について解説しますね。たまに、関数の引数で_を見かけることがあるかと思います。この引数を無視するパラメータ_は、関数やメソッドの引数のうち、使用されないものを明示的に示す記法です。

開発環境 バージョン
Next.js 13.4.4
TypeScript 5.0.4
Emotion 11.11.0
React 18.2.0

引数を無視するパラメータ_とは?

初めに、引数を無視するパラメータ_とは何かを説明いたします。JavaScript や TypeScript を使って関数を書く時、関数が引数を受け取ることがあります。これらの引数は、関数内で具体的な動作を行うための入力値となります。

しかし、時として関数の中で全ての引数を使う必要がない場合があります。特に TypeScript を使用すると、型システムが全ての引数を要求する場合もあります。ここで引数を無視するパラメータ_が活躍します。この記法を使用すると、引数が関数内で使用されないことを明示的に示せます。

以下の TypeScript のソースコードは、その例を示しています。

type Props = {
  name: string
  age: number
}

const Component = ({ name, _ }: Props) => {
  return <div>{name}</div>
}

この例では、Componentという関数がProps型の引数を受け取ります。ここで、_という引数は、Props型のageフィールドを表していますが、関数の中で全く使われていません。これが、引数を無視するパラメータ_の一例です。

モック関数やテストコードでの使用

JavaScript や TypeScript でテストコードを書く際には、特定の関数をモック(つまり偽の関数)に置き換えて、その関数が呼ばれたことだけを確認することがあります。こうした場合、関数の実装自体は重要ではなく、引数も無視されることが多いです。ここで_を使用することで、引数が無視されることを明示的に示すことができます。

jest.mock('./path/to/module', () => ({
  someFunction: (_: any) => {
    // 実装は重要ではない、引数も無視
  },
}))

Promise.all の結果を無視する

JavaScript のPromise.all関数は、複数の Promise を並行して実行し、それら全てが解決されたときに結果を返します。しかし、全ての結果が必要でない場合、_を使用して無視することができます。

const promise1 = fetchDataFromAPI1()
const promise2 = fetchDataFromAPI2() // この結果は無視する

Promise.all([promise1, promise2]).then(([data1, _]) => {
  // promise2の結果は無視し、data1だけを利用する
  console.log(data1)
})

イベントハンドラーでイベントオブジェクトを無視する

ブラウザや React 等のフロントエンドのフレームワークでは、イベントハンドラー(ボタンのクリックなどのイベントを処理する関数)には、デフォルトでイベントオブジェクトが引数として渡されます。しかし、このイベントオブジェクトは必ずしも利用されるわけではありません。この場合も、_を使用してイベントオブジェクトを無視することができます。

const handleClick = (_: React.MouseEvent) => {
  // イベントオブジェクトは無視し、固定の処理を行う
  console.log('Button clicked!')
}

;<button onClick={handleClick}>Click me!</button>

このように、引数を無視するパラメータ_は、さまざまな場面で利用することが可能です。無視される引数を明示的に示すことで、コードの可読性を高め、何が重要で何が重要でないかを明示的に示すことができます。

Next.js で、引数を無視するパラメータ_を実装

では、Next.js でこの引数を無視するパラメータ_をどのように利用できるのか見ていきましょう。

// pages

/index.tsx

import type { NextPage, GetServerSideProps } from 'next'

type Props = {
  data: string,
}

const Home: NextPage<Props> = ({ data }) => {
  return <div>{data}</div>
}

export const getServerSideProps: GetServerSideProps<Props> = async (_) => {
  const data = 'Hello, world!'
  return { props: { data } }
}

export default Home

このコードは、Next.js のサーバーサイドレンダリングの一例です。ここで注目すべきは、getServerSideProps関数の引数部分です。この関数は、contextという引数を受け取ることが一般的ですが、今回の例ではその引数が_になっています。つまり、contextはこの関数の中で一切使われないことを示しています。こうすることで、コードの読み手に対して関数が何を期待しているか、何を利用していないかを明確に伝えることができます。

引数を無視するパラメータ_を実装

ここで、さらに進んだテクニカルな例を見てみましょう。この例では、配列の分割代入を用いた際の引数を無視するパラメータ_の使用を見ていきます。

const array = ['apple', 'banana', 'cherry']

const [first, _, third] = array

console.log(first) // "apple"
console.log(third) // "cherry"

この例では、配列arrayから分割代入を行っています。分割代入では、配列の要素を個別の変数に一度に代入することができます。ここで、_は配列の 2 番目の要素('banana')を受け取っていますが、それが後続のコードで使用されることはありません。

このように、引数を無視するパラメータ_を用いることで、コードの可読性を高め、何が重要で何が重要でないかを明示的に示すことができます。

Next.js と TypeScript で、関数の引数を無視するパラメータ`_`の使い所