かもメモ

自分の落ちた落とし穴に何度も落ちる人のメモ帳

Node.js ファイル名から拡張子を取得したい

正引き表現や . で区切る方法を考えてたけど path を使えば簡単だった

path.extname(path) で拡張子を取得できる

path.extname で取得できる拡張子は . 始まりの文字列
拡張子が無い場合は空文字列が返される
サーチクエリがある場合は拡張子含まれる

import path from "path";

path.extname('index.html');
// -> '.html'
path.extname('index.coffee.md');
// -> '.md'
path.extname('index.');
// -> '.'
path.extname('index');
// -> ''
path.extname('.index');
// -> ''
path.extname('.index.md');
// -> '.md' 
path.extname('/aikatsu/idol/ichigo.md?foo=bar');
// -> '.md?foo=bar' 

cf. Path | Node.js v21.7.2 Documentation

ファイル名・拡張子を別々に取得したいときは path.parse(path) が便利

path.parse()root, dir (ファイルまでのパス), base (ファイル名 + 拡張子), name (ファイル名), ext (拡張子) のオブジェクトを返す

import path from "path";

path.parse('/home/user/dir/file.txt');
// { root: '/',
//   dir: '/home/user/dir',
//   base: 'file.txt',
//   name: 'file',
//   ext: '.txt' }

const pathData = path.parse('./aikatsu/idol/ichigo.md?foo=bar');
// { root: '',
//   dir: './aikatsu/idol',
//   base: 'ichigo.md?foo=bar',
//   name: 'ichigo',
//   ext: '.md?foo=bar' }

該当するものがない場合は空文字になる

おわり ₍ᐢ..ᐢ₎


[参考]

今年度もアイカツ!

JavaScript JSON を見やすく出力する

pre とかにデータを JSON にして表示したい時に 1行だと見づらいのいい感じに改行して表示させたい

JSON.stringify() のオプションでいい感じに表示できる

json-formatter-js とかリッチなライブラリもあるけど、必要最小限なら JSON.stringify(data, null, 2) で事足りた

const data = [
  {name: 'Hosimiya Ichigo', type: 'cute'},
  {name: 'Kiriya Aoi', type: 'cool'},
  {name: 'Shibuki Ran', type: 'sexy'},
];

const App: FC = () => {
  return (
    <pre styles={{whiteSpace: "preWrap"}}>
     {JSON.stringify(data, null, 2)}
    </pre>
  );
}

↓ TAB space 2 でいい感じに改行された JSON が表示できた

[
  {
    "name": "Hosimiya Ichigo",
    "type": "cute"
  },
  {
    "name": "Kiriya Aoi",
    "type": "cool"
  },
  {
    "name": "Shibuki Ran",
    "type": "sexy"
  }
]

おわり


[参考]

TypeScript Object.entries の型をいい感じにしたい

環境

  • TypeScript v5

引数のオブジェクトを Record<string, unknown> とするパターン

返り値に as を使わないとタイプエラーになる

返り値 Entries を定義するパターン

type Entries<T> = (keyof T extends infer U
  ? U extends keyof T
    ? [U, T[U]]
    : unknown
  : unknown)[];

export const strictEntries = <T extends Record<string, unknown>>(
  object: T,
): Entries<T> => {
  return Object.entries(object) as Entries<T>;
};

return Object.entries(object) as Entries<T>; にしないと type error になる

返り値を [keyof T, T[keyof T]][] とするパターン

export const strictEntries = <T extends Record<string, unknown>>(
  object: T,
): [keyof T, T[keyof T]][] => {
  return Object.entries(object) as [keyof T, T[keyof T]][];
};

return Object.entries(object) as [keyof T, T[keyof T]][]; にしないと type error になる

オブジェクトを Record<string, any> にすれば返り値を [keyof T, T[keyof T]][] にすれば as を使わなくても良い

export const strictEntries = <T extends Record<string, any>>(
  object: T,
): [keyof T, T[keyof T]][] => {
  return Object.entries(object);
};

これなら type error にならない

詳しい挙動は調べてないが、どちらでもいい感じに形推論されるようになったからヨシ
おわり


[参考]