TypeScriptã§å ç¢ãªNode.jsãã¡ã€ã«æäœãç¿åŸããŸãããããã®å æ¬çãªã¬ã€ãã§ã¯ãåæãéåæãã¹ããªãŒã ããŒã¹ã®FSã¡ãœãããæ¢æ±ããã°ããŒãã«éçºããŒã åãã®åå®å šæ§ããšã©ãŒåŠçããã¹ããã©ã¯ãã£ã¹ã«çŠç¹ãåœãŠãŸãã
TypeScriptãã¡ã€ã«ã·ã¹ãã ç¿åŸ: ã°ããŒãã«éçºè ã®ããã®åå®å šãªNode.jsãã¡ã€ã«æäœ
çŸä»£ã®ãœãããŠã§ã¢éçºã®åºå€§ãªé åã«ãããŠãNode.jsã¯ã¹ã±ãŒã©ãã«ãªãµãŒããŒãµã€ãã¢ããªã±ãŒã·ã§ã³ãã³ãã³ãã©ã€ã³ããŒã«ãªã©ãæ§ç¯ããããã®åŒ·åãªã©ã³ã¿ã€ã ãšããŠç¢ºç«ãããŠããŸããå€ãã®Node.jsã¢ããªã±ãŒã·ã§ã³ã«ãããåºæ¬çãªåŽé¢ã¯ããã¡ã€ã«ã·ã¹ãã ã®æäœãããªãã¡ãã¡ã€ã«ã®èªã¿æžããäœæã管çãããã³ãã£ã¬ã¯ããªã®æäœãå«ã¿ãŸããJavaScriptã¯ãããã®æäœãæè»ã«åŠçããèœåãæäŸããŸãããTypeScriptã®å°å ¥ã«ãããéçåãã§ãã¯ã匷åãããããŒã«ããããŠæçµçã«ã¯ãã¡ã€ã«ã·ã¹ãã ã³ãŒãã®ä¿¡é Œæ§ãšä¿å®æ§ãåäžãããã®äœéšãããã«é«ãŸããŸãã
ãã®å æ¬çãªã¬ã€ãã¯ãTypeScriptãæäŸããå ç¢æ§ããã£ãŠNode.jsãã¡ã€ã«æäœãç¿åŸããããšèãããæåçãªèæ¯ãå°ççãªå Žæã«ââé¢ããããäžçäžã®éçºè ã察象ãšããŠããŸããç§ãã¡ã¯ã³ã¢ãšãªã`fs`ã¢ãžã¥ãŒã«ãæ·±ãæãäžãããã®æ§ã ãªåæããã³éåæãã©ãã€ã ãæ¢æ±ããææ°ã®PromiseããŒã¹APIãæ€èšŒããTypeScriptã®åã·ã¹ãã ãããã«äžè¬çãªãšã©ãŒãå€§å¹ ã«åæžããã³ãŒãã®æç¢ºæ§ãåäžãããããšãã§ããããæããã«ããŸãã
åºç€: Node.jsãã¡ã€ã«ã·ã¹ãã (`fs`)ã®çè§£
Node.jsã®`fs`ã¢ãžã¥ãŒã«ã¯ãæšæºã®POSIX颿°ãã¢ãã«ãšããæ¹æ³ã§ãã¡ã€ã«ã·ã¹ãã ãšå¯Ÿè©±ããããã®APIãæäŸããŸããåºæ¬çãªãã¡ã€ã«ã®èªã¿æžãããè€éãªãã£ã¬ã¯ããªæäœããã¡ã€ã«ç£èŠã«è³ããŸã§ãå¹ åºãã¡ãœãããæäŸããŸããäŒçµ±çã«ããããã®æäœã¯ã³ãŒã«ããã¯ã§åŠçãããŠããŸããããè€éãªã·ããªãªã§ã¯æªåé«ããã³ãŒã«ããã¯å°çãã«ã€ãªãã£ãŠããŸãããNode.jsã®é²åã«äŒŽããPromiseãš`async/await`ãéåææäœã®æšå¥šãã¿ãŒã³ãšããŠç»å Žããã³ãŒããããèªã¿ãããã管çããããããŸããã
ãã¡ã€ã«ã·ã¹ãã æäœã«TypeScriptã䜿çšããçç±
Node.jsã®`fs`ã¢ãžã¥ãŒã«ã¯ãã¬ãŒã³ãªJavaScriptã§ãå®å šã«æ©èœããŸãããTypeScriptãçµ±åããããšã§ããã€ãã®é åçãªå©ç¹ãåŸãããŸãã
- åå®å šæ§: ã³ãŒããå®è¡ãããåã«ãã³ã³ãã€ã«æã«èª€ã£ãåŒæ°ã®åãäžè¶³ããŠãããã©ã¡ãŒã¿ãŒãäºæããªãæ»ãå€ãªã©ã®äžè¬çãªãšã©ãŒãææããŸããããã¯ãæ§ã ãªãã¡ã€ã«ãšã³ã³ãŒãã£ã³ã°ããã©ã°ã`Buffer`ãªããžã§ã¯ããæ±ãéã«éåžžã«è²Žéã§ãã
- èªã¿ãããã®åäž: æç€ºçãªåã¢ãããŒã·ã§ã³ã«ããã颿°ãã©ã®ãããªçš®é¡ã®ããŒã¿ãæåŸ ããäœãè¿ãããæç¢ºã«ãªãã倿§ãªããŒã ã®éçºè ã«ãšã£ãŠã³ãŒãã®ç解床ãåäžããŸãã
- åªããããŒã«ãšãªãŒãã³ã³ããªãŒã: IDEïŒVS Codeãªã©ïŒã¯TypeScriptã®åå®çŸ©ã掻çšããŠãã€ã³ããªãžã§ã³ããªãªãŒãã³ã³ããªãŒãããã©ã¡ãŒã¿ãŒãã³ããã€ã³ã©ã€ã³ããã¥ã¡ã³ããæäŸããçç£æ§ãå€§å¹ ã«åäžãããŸãã
- ãªãã¡ã¯ã¿ãªã³ã°ã®ä¿¡é Œæ§: ã€ã³ã¿ãŒãã§ãŒã¹ã颿°ã·ã°ããã£ã倿ŽãããšãTypeScriptã¯åœ±é¿ãåãããã¹ãŠã®é åãããã«éç¥ãããããå€§èŠæš¡ãªãªãã¡ã¯ã¿ãªã³ã°ã§ã®ãšã©ãŒçºçãæžããããšãã§ããŸãã
- ã°ããŒãã«ãªäžè²«æ§: åœéçãªéçºããŒã å šäœã§äžè²«ããã³ãŒãã£ã³ã°ã¹ã¿ã€ã«ãšããŒã¿æ§é ã®çè§£ãä¿èšŒããææ§ãã軜æžããŸãã
åææäœ vs. éåææäœ: ã°ããŒãã«ãªèŠç¹
ç¹ã«ããã©ãŒãã³ã¹ãšå¿çæ§ãæéèŠã§ããã°ããŒãã«å±éåãã®ã¢ããªã±ãŒã·ã§ã³ãæ§ç¯ããå Žåãåææäœãšéåææäœã®éããçè§£ããããšã¯éåžžã«éèŠã§ããã»ãšãã©ã®`fs`ã¢ãžã¥ãŒã«é¢æ°ã«ã¯ãåæãšéåæã®ããªã¢ã³ãããããŸããçµéšåãšããŠãNode.jsãµãŒããŒã®å¿çæ§ãç¶æããããã«äžå¯æ¬ ãªéããããã³ã°I/Oæäœã«ã¯ãéåæã¡ãœãããæšå¥šãããŸãã
- éåæ (ãã³ããããã³ã°): ãããã®ã¡ãœããã¯ãæåŸã®åŒæ°ãšããŠã³ãŒã«ããã¯é¢æ°ãåãåããã`Promise`ãè¿ããŸãããã¡ã€ã«ã·ã¹ãã æäœãéå§ãããšããã«æ»ããä»ã®ã³ãŒãã®å®è¡ãèš±å¯ããŸããæäœãå®äºãããšãã³ãŒã«ããã¯ãåŒã³åºããããïŒãŸãã¯Promiseã解決/æåŠãããïŒãŸããããã¯ãäžçäžã®ãŠãŒã¶ãŒããã®è€æ°ã®åæãªã¯ãšã¹ããåŠçãããµãŒããŒã¢ããªã±ãŒã·ã§ã³ã«æé©ã§ããããã¡ã€ã«æäœã®å®äºãåŸ ã£ãŠããéã«ãµãŒããŒãããªãŒãºããã®ãé²ããŸãã
- åæ (ããããã³ã°): ãããã®ã¡ãœããã¯ãæ»ãåã«æäœãå®å šã«å®è¡ããŸããã³ãŒãã£ã³ã°ã¯åçŽã§ãããNode.jsã€ãã³ãã«ãŒãããããã¯ãããã¡ã€ã«ã·ã¹ãã æäœãå®äºãããŸã§ä»ã®ã³ãŒããå®è¡ãããã®ãé²ããŸããããã¯ãç¹ã«ãã©ãã£ãã¯ã®å€ãç°å¢ã§ã¯ãé倧ãªããã©ãŒãã³ã¹ããã«ããã¯ãšå¿çæ§ã®ãªãã¢ããªã±ãŒã·ã§ã³ã«ã€ãªããå¯èœæ§ããããŸããåææäœã¯ãã¢ããªã±ãŒã·ã§ã³ã®èµ·åããžãã¯ããããããã³ã°ã蚱容ãããåçŽãªã¹ã¯ãªãããªã©ãéãããç¶æ³ã§ã®ã¿äœ¿çšããŠãã ããã
TypeScriptã«ãããäž»èŠãªãã¡ã€ã«æäœã¿ã€ã
äžè¬çãªãã¡ã€ã«ã·ã¹ãã æäœã«ãããTypeScriptã®å®éã®å¿çšã«ã€ããŠèŠãŠãããŸããããNode.jsã®çµã¿èŸŒã¿åå®çŸ©ã䜿çšããŸãããããã¯éåžžã`@types/node`ããã±ãŒãžãéããŠå©çšã§ããŸãã
éå§ããã«ã¯ãTypeScriptãšNode.jsã®åããããžã§ã¯ãã«ã€ã³ã¹ããŒã«ãããŠããããšã確èªããŠãã ããã
npm install typescript @types/node --save-dev
`tsconfig.json`ã¯é©åã«èšå®ãããŠããå¿ èŠããããŸããäŸïŒ
{
"compilerOptions": {
"target": "es2020",
"module": "commonjs",
"outDir": "./dist",
"strict": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true
},
"include": ["src/**/*"]
}
ãã¡ã€ã«ã®èªã¿èŸŒã¿: `readFile`, `readFileSync`, ããã³Promises API
ãã¡ã€ã«ããã³ã³ãã³ããèªã¿åãããšã¯åºæ¬çãªæäœã§ããTypeScriptã¯ããã¡ã€ã«ãã¹ããšã³ã³ãŒãã£ã³ã°ãããã³æœåšçãªãšã©ãŒãæ£ããåŠçããã®ã«åœ¹ç«ã¡ãŸãã
éåæãã¡ã€ã«èªã¿èŸŒã¿ (ã³ãŒã«ããã¯ããŒã¹)
`fs.readFile`颿°ã¯ãéåæãã¡ã€ã«èªã¿èŸŒã¿ã®äžæ žããªã颿°ã§ãããã¹ããªãã·ã§ã³ã®ãšã³ã³ãŒãã£ã³ã°ãããã³ã³ãŒã«ããã¯é¢æ°ãåãåããŸããTypeScriptã¯ãã³ãŒã«ããã¯ã®åŒæ°ãæ£ããåä»ããããŠããããšïŒ`Error | null`ã`Buffer | string`ïŒãä¿èšŒããŸãã
import * as fs from 'fs';
const filePath: string = 'data/example.txt';
fs.readFile(filePath, 'utf8', (err: NodeJS.ErrnoException | null, data: string) => {
if (err) {
// Log error for international debugging, e.g., 'File not found'
console.error(`Error reading file '${filePath}': ${err.message}`);
return;
}
// Process file content, ensuring it's a string as per 'utf8' encoding
console.log(`File content (${filePath}):\n${data}`);
});
// Example: Reading binary data (no encoding specified)
const binaryFilePath: string = 'data/image.png';
fs.readFile(binaryFilePath, (err: NodeJS.ErrnoException | null, data: Buffer) => {
if (err) {
console.error(`Error reading binary file '${binaryFilePath}': ${err.message}`);
return;
}
// 'data' is a Buffer here, ready for further processing (e.g., streaming to a client)
console.log(`Read ${data.byteLength} bytes from ${binaryFilePath}`);
});
åæãã¡ã€ã«èªã¿èŸŒã¿
`fs.readFileSync`ã¯ã€ãã³ãã«ãŒãããããã¯ããŸãããã®æ»ãå€ã®åã¯ããšã³ã³ãŒãã£ã³ã°ãæäŸãããŠãããã©ããã«å¿ããŠ`Buffer`ãŸãã¯`string`ã§ããTypeScriptã¯ãããæ£ããæšè«ããŸãã
import * as fs from 'fs';
const syncFilePath: string = 'data/sync_example.txt';
try {
const content: string = fs.readFileSync(syncFilePath, 'utf8');
console.log(`Synchronous read content (${syncFilePath}):\n${content}`);
} catch (error: any) {
console.error(`Synchronous read error for '${syncFilePath}': ${error.message}`);
}
PromiseããŒã¹ã®ãã¡ã€ã«èªã¿èŸŒã¿ (`fs/promises`)
ææ°ã®`fs/promises` APIã¯ãéåææäœã«éåžžã«æšå¥šããããããã¯ãªãŒã³ãªPromiseããŒã¹ã®ã€ã³ã¿ãŒãã§ãŒã¹ãæäŸããŸããTypeScriptã¯ãç¹ã«`async/await`ã§ããã§åªããæ©èœãçºæ®ããŸãã
import * as fsPromises from 'fs/promises';
async function readTextFile(path: string): Promise
ãã¡ã€ã«ã®æžã蟌ã¿: `writeFile`, `writeFileSync`, ããã³ãã©ã°
ãã¡ã€ã«ãžã®ããŒã¿ã®æžã蟌ã¿ãåæ§ã«éèŠã§ããTypeScriptã¯ããã¡ã€ã«ãã¹ãããŒã¿åïŒæååãŸãã¯BufferïŒããšã³ã³ãŒãã£ã³ã°ãããã³ãã¡ã€ã«ãªãŒãã³ãã©ã°ã®ç®¡çã«åœ¹ç«ã¡ãŸãã
éåæãã¡ã€ã«æžã蟌ã¿
`fs.writeFile`ã¯ããã¡ã€ã«ã«ããŒã¿ãæžã蟌ãããã«äœ¿çšãããããã©ã«ãã§ã¯ãã¡ã€ã«ãæ¢ã«ååšããå Žåã¯çœ®æããŸãããã®åäœã¯`flags`ã§å¶åŸ¡ã§ããŸãã
import * as fs from 'fs';
const outputFilePath: string = 'data/output.txt';
const fileContent: string = 'This is new content written by TypeScript.';
fs.writeFile(outputFilePath, fileContent, 'utf8', (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error writing file '${outputFilePath}': ${err.message}`);
return;
}
console.log(`File '${outputFilePath}' written successfully.`);
});
// Example with Buffer data
const bufferContent: Buffer = Buffer.from('Binary data example');
const binaryOutputFilePath: string = 'data/binary_output.bin';
fs.writeFile(binaryOutputFilePath, bufferContent, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error writing binary file '${binaryOutputFilePath}': ${err.message}`);
return;
}
console.log(`Binary file '${binaryOutputFilePath}' written successfully.`);
});
åæãã¡ã€ã«æžã蟌ã¿
`fs.writeFileSync`ã¯ãæžãèŸŒã¿æäœãå®äºãããŸã§ã€ãã³ãã«ãŒãããããã¯ããŸãã
import * as fs from 'fs';
const syncOutputFilePath: string = 'data/sync_output.txt';
try {
fs.writeFileSync(syncOutputFilePath, 'Synchronously written content.', 'utf8');
console.log(`File '${syncOutputFilePath}' written synchronously.`);
} catch (error: any) {
console.error(`Synchronous write error for '${syncOutputFilePath}': ${error.message}`);
}
PromiseããŒã¹ã®ãã¡ã€ã«æžã蟌㿠(`fs/promises`)
`async/await`ãš`fs/promises`ã䜿çšããææ°ã®ã¢ãããŒãã¯ãéåææžã蟌ã¿ã管çããããã«ããã¯ãªãŒã³ãªããšãå€ãã§ãã
import * as fsPromises from 'fs/promises';
import { constants as fsConstants } from 'fs'; // For flags
async function writeDataToFile(path: string, data: string | Buffer): Promise
éèŠãªãã©ã°:
- `'w'` (ããã©ã«ã): æžã蟌ã¿çšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ã¯äœæããããïŒååšããªãå ŽåïŒãåãè©°ããããŸãïŒååšããå ŽåïŒã
- `'w+'`: èªã¿åãããã³æžã蟌ã¿çšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ã¯äœæããããïŒååšããªãå ŽåïŒãåãè©°ããããŸãïŒååšããå ŽåïŒã
- `'a'` (远å ): 远å çšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ãååšããªãå Žåã¯äœæãããŸãã
- `'a+'`: èªã¿åãããã³è¿œå çšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ãååšããªãå Žåã¯äœæãããŸãã
- `'r'` (èªã¿åã): èªã¿åãçšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ãååšããªãå Žåã¯äŸå€ãçºçããŸãã
- `'r+'`: èªã¿åãããã³æžã蟌ã¿çšã«ãã¡ã€ã«ãéããŸãããã¡ã€ã«ãååšããªãå Žåã¯äŸå€ãçºçããŸãã
- `'wx'` (æä»çæžã蟌ã¿): `'w'`ã«äŒŒãŠããŸããããã¹ãååšããå Žåã¯å€±æããŸãã
- `'ax'` (æä»ç远å ): `'a'`ã«äŒŒãŠããŸããããã¹ãååšããå Žåã¯å€±æããŸãã
ãã¡ã€ã«ãžã®è¿œå : `appendFile`, `appendFileSync`
æ¢åã®ãã¡ã€ã«ã®å 容ãäžæžãããã«ããŒã¿ã®æ«å°Ÿã«è¿œå ããå¿ èŠãããå Žåã¯ã`appendFile`ãéžæããŸããããã¯ããã°èšé²ãããŒã¿åéãç£æ»èšŒè·¡ã«ç¹ã«åœ¹ç«ã¡ãŸãã
éåæè¿œå
import * as fs from 'fs';
const logFilePath: string = 'data/app_logs.log';
function logMessage(message: string): void {
const timestamp: string = new Date().toISOString();
const logEntry: string = `${timestamp} - ${message}\n`;
fs.appendFile(logFilePath, logEntry, 'utf8', (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error appending to log file '${logFilePath}': ${err.message}`);
return;
}
console.log(`Logged message to '${logFilePath}'.`);
});
}
logMessage('User "Alice" logged in.');
setTimeout(() => logMessage('System update initiated.'), 50);
logMessage('Database connection established.');
åæè¿œå
import * as fs from 'fs';
const syncLogFilePath: string = 'data/sync_app_logs.log';
function logMessageSync(message: string): void {
const timestamp: string = new Date().toISOString();
const logEntry: string = `${timestamp} - ${message}\n`;
try {
fs.appendFileSync(syncLogFilePath, logEntry, 'utf8');
console.log(`Logged message synchronously to '${syncLogFilePath}'.`);
} catch (error: any) {
console.error(`Synchronous error appending to log file '${syncLogFilePath}': ${error.message}`);
}
}
logMessageSync('Application started.');
logMessageSync('Configuration loaded.');
PromiseããŒã¹ã®è¿œå (`fs/promises`)
import * as fsPromises from 'fs/promises';
const promiseLogFilePath: string = 'data/promise_app_logs.log';
async function logMessagePromise(message: string): Promise
ãã¡ã€ã«ã®åé€: `unlink`, `unlinkSync`
ãã¡ã€ã«ã·ã¹ãã ãããã¡ã€ã«ãåé€ããŸããTypeScriptã¯ãæå¹ãªãã¹ãæž¡ãããšã©ãŒãæ£ããåŠçããã®ã«åœ¹ç«ã¡ãŸãã
éåæåé€
import * as fs from 'fs';
const fileToDeletePath: string = 'data/temp_to_delete.txt';
// First, create the file to ensure it exists for deletion demo
fs.writeFile(fileToDeletePath, 'Temporary content.', 'utf8', (err) => {
if (err) {
console.error('Error creating file for deletion demo:', err);
return;
}
console.log(`File '${fileToDeletePath}' created for deletion demo.`);
fs.unlink(fileToDeletePath, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error deleting file '${fileToDeletePath}': ${err.message}`);
return;
}
console.log(`File '${fileToDeletePath}' deleted successfully.`);
});
});
åæåé€
import * as fs from 'fs';
const syncFileToDeletePath: string = 'data/sync_temp_to_delete.txt';
try {
fs.writeFileSync(syncFileToDeletePath, 'Sync temp content.', 'utf8');
console.log(`File '${syncFileToDeletePath}' created.`);
fs.unlinkSync(syncFileToDeletePath);
console.log(`File '${syncFileToDeletePath}' deleted synchronously.`);
} catch (error: any) {
console.error(`Synchronous deletion error for '${syncFileToDeletePath}': ${error.message}`);
}
PromiseããŒã¹ã®åé€ (`fs/promises`)
import * as fsPromises from 'fs/promises';
const promiseFileToDeletePath: string = 'data/promise_temp_to_delete.txt';
async function deleteFile(path: string): Promise
ãã¡ã€ã«ã®ååšãã§ãã¯ãšæš©é: `existsSync`, `access`, `accessSync`
ãã¡ã€ã«ãæäœããåã«ããã¡ã€ã«ãååšããããçŸåšã®ããã»ã¹ã«å¿ èŠãªæš©éããããã確èªããå¿ èŠããããããããŸãããTypeScriptã¯ã`mode`ãã©ã¡ãŒã¿ãŒã®åãæäŸããããšã§ãããæ¯æŽããŸãã
åæååšãã§ãã¯
`fs.existsSync`ã¯åçŽãªåæãã§ãã¯ã§ãã䟿å©ã§ãããç«¶åç¶æ ã®è匱æ§ãããããïŒ`existsSync`ãšãã®åŸã®æäœã®éã«ãã¡ã€ã«ãåé€ãããå¯èœæ§ãããïŒãéèŠãªæäœã«ã¯`fs.access`ã䜿çšããæ¹ãè¯ãããšããããããŸãã
import * as fs from 'fs';
const checkFilePath: string = 'data/example.txt';
if (fs.existsSync(checkFilePath)) {
console.log(`File '${checkFilePath}' exists.`);
} else {
console.log(`File '${checkFilePath}' does not exist.`);
}
éåææš©éãã§ã㯠(`fs.access`)
`fs.access`ã¯ã`path`ã§æå®ããããã¡ã€ã«ãŸãã¯ãã£ã¬ã¯ããªã«å¯ŸãããŠãŒã¶ãŒã®æš©éããã¹ãããŸããããã¯éåæã§ããã`mode`åŒæ°ïŒäŸïŒååšç¢ºèªã®ããã®`fs.constants.F_OK`ãèªã¿åãã®ããã®`R_OK`ãæžã蟌ã¿ã®ããã®`W_OK`ãå®è¡ã®ããã®`X_OK`ïŒãåãåããŸãã
import * as fs from 'fs';
import { constants } from 'fs';
const accessFilePath: string = 'data/example.txt';
fs.access(accessFilePath, constants.F_OK, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`File '${accessFilePath}' does not exist or access denied.`);
return;
}
console.log(`File '${accessFilePath}' exists.`);
});
fs.access(accessFilePath, constants.R_OK | constants.W_OK, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`File '${accessFilePath}' is not readable/writable or access denied: ${err.message}`);
return;
}
console.log(`File '${accessFilePath}' is readable and writable.`);
});
PromiseããŒã¹ã®æš©éãã§ã㯠(`fs/promises`)
import * as fsPromises from 'fs/promises';
import { constants } from 'fs';
async function checkFilePermissions(path: string, mode: number): Promise
ãã¡ã€ã«æ å ±ã®ååŸ: `stat`, `statSync`, `fs.Stats`
`fs.stat`ãã¡ããªãŒã®é¢æ°ã¯ããµã€ãºãäœææ¥æã倿޿¥æãæš©éãªã©ããã¡ã€ã«ãŸãã¯ãã£ã¬ã¯ããªã«é¢ãã詳现æ å ±ãæäŸããŸããTypeScriptã®`fs.Stats`ã€ã³ã¿ãŒãã§ãŒã¹ã¯ããã®ããŒã¿ãéåžžã«æ§é åãããä¿¡é Œæ§ã®é«ããã®ãšããŠæ±ããããã«ããŸãã
éåæStat
import * as fs from 'fs';
import { Stats } from 'fs';
const statFilePath: string = 'data/example.txt';
fs.stat(statFilePath, (err: NodeJS.ErrnoException | null, stats: Stats) => {
if (err) {
console.error(`Error getting stats for '${statFilePath}': ${err.message}`);
return;
}
console.log(`Stats for '${statFilePath}':`);
console.log(` Is file: ${stats.isFile()}`);
console.log(` Is directory: ${stats.isDirectory()}`);
console.log(` Size: ${stats.size} bytes`);
console.log(` Creation time: ${stats.birthtime.toISOString()}`);
console.log(` Last modified: ${stats.mtime.toISOString()}`);
});
PromiseããŒã¹ã®Stat (`fs/promises`)
import * as fsPromises from 'fs/promises';
import { Stats } from 'fs'; // Still use the 'fs' module's Stats interface
async function getFileStats(path: string): Promise
TypeScriptã§ã®ãã£ã¬ã¯ããªæäœ
ãã£ã¬ã¯ããªã®ç®¡çã¯ããã¡ã€ã«ãæŽçããããã¢ããªã±ãŒã·ã§ã³åºæã®ã¹ãã¬ãŒãžãäœæããããäžæããŒã¿ãåŠçãããããããã®äžè¬çãªèŠä»¶ã§ããTypeScriptã¯ããããã®æäœã«å ç¢ãªåä»ããæäŸããŸãã
ãã£ã¬ã¯ããªã®äœæ: `mkdir`, `mkdirSync`
`fs.mkdir`颿°ã¯ãæ°ãããã£ã¬ã¯ããªãäœæããããã«äœ¿çšãããŸãã`recursive`ãªãã·ã§ã³ã¯ã芪ãã£ã¬ã¯ããªããŸã ååšããªãå Žåã«ããããäœæããã®ã«éåžžã«åœ¹ç«ã¡ãUnixã©ã€ã¯ãªã·ã¹ãã ã«ããã`mkdir -p`ã®åäœãæš¡å£ããŸãã
éåæãã£ã¬ã¯ããªäœæ
import * as fs from 'fs';
const newDirPath: string = 'data/new_directory';
const recursiveDirPath: string = 'data/nested/path/to/create';
// Create a single directory
fs.mkdir(newDirPath, (err: NodeJS.ErrnoException | null) => {
if (err) {
// Ignore EEXIST error if directory already exists
if (err.code === 'EEXIST') {
console.log(`Directory '${newDirPath}' already exists.`);
} else {
console.error(`Error creating directory '${newDirPath}': ${err.message}`);
}
return;
}
console.log(`Directory '${newDirPath}' created successfully.`);
});
// Create nested directories recursively
fs.mkdir(recursiveDirPath, { recursive: true }, (err: NodeJS.ErrnoException | null) => {
if (err) {
if (err.code === 'EEXIST') {
console.log(`Directory '${recursiveDirPath}' already exists.`);
} else {
console.error(`Error creating recursive directory '${recursiveDirPath}': ${err.message}`);
}
return;
}
console.log(`Recursive directories '${recursiveDirPath}' created successfully.`);
});
PromiseããŒã¹ã®ãã£ã¬ã¯ããªäœæ (`fs/promises`)
import * as fsPromises from 'fs/promises';
async function createDirectory(path: string, recursive: boolean = false): Promise
ãã£ã¬ã¯ããªå 容ã®èªã¿åã: `readdir`, `readdirSync`, `fs.Dirent`
æå®ããããã£ã¬ã¯ããªå ã®ãã¡ã€ã«ãšãµããã£ã¬ã¯ããªããªã¹ãããã«ã¯ã`fs.readdir`ã䜿çšããŸãã`withFileTypes`ãªãã·ã§ã³ã¯ãåã ã®ãšã³ããªã`stat`ããããšãªããããè©³çŽ°ãªæ å ±ãçŽæ¥æäŸãã`fs.Dirent`ãªããžã§ã¯ããè¿ãææ°ã®è¿œå æ©èœã§ãã
éåæãã£ã¬ã¯ããªèªã¿åã
import * as fs from 'fs';
const readDirPath: string = 'data';
fs.readdir(readDirPath, (err: NodeJS.ErrnoException | null, files: string[]) => {
if (err) {
console.error(`Error reading directory '${readDirPath}': ${err.message}`);
return;
}
console.log(`Contents of directory '${readDirPath}':`);
files.forEach(file => {
console.log(` - ${file}`);
});
});
// With `withFileTypes` option
fs.readdir(readDirPath, { withFileTypes: true }, (err: NodeJS.ErrnoException | null, dirents: fs.Dirent[]) => {
if (err) {
console.error(`Error reading directory with file types '${readDirPath}': ${err.message}`);
return;
}
console.log(`Contents of directory '${readDirPath}' (with types):`);
dirents.forEach(dirent => {
const type: string = dirent.isFile() ? 'File' : dirent.isDirectory() ? 'Directory' : 'Other';
console.log(` - ${dirent.name} (${type})`);
});
});
PromiseããŒã¹ã®ãã£ã¬ã¯ããªèªã¿åã (`fs/promises`)
import * as fsPromises from 'fs/promises';
import { Dirent } from 'fs'; // Still use 'fs' module's Dirent interface
async function listDirectoryContents(path: string): Promise
ãã£ã¬ã¯ããªã®åé€: `rmdir` (éæšå¥š), `rm`, `rmSync`
Node.jsã¯ãã£ã¬ã¯ããªåé€ã¡ãœãããé²åãããŠããŸããã`fs.rmdir`ã¯çŸåšãååž°çãªåé€ã®ããã«`fs.rm`ã«ã»ãŒçœ®ãæããããŠãããããå ç¢ã§äžè²«æ§ã®ããAPIãæäŸããŠããŸãã
éåæãã£ã¬ã¯ããªåé€ (`fs.rm`)
`fs.rm`颿°ïŒNode.js 14.14.0以éã§å©çšå¯èœïŒã¯ããã¡ã€ã«ããã³ãã£ã¬ã¯ããªãåé€ããããã®æšå¥šãããæ¹æ³ã§ãã`recursive: true`ãªãã·ã§ã³ã¯ã空ã§ãªããã£ã¬ã¯ããªãåé€ããããã«éèŠã§ãã
import * as fs from 'fs';
const dirToDeletePath: string = 'data/dir_to_delete';
const nestedDirToDeletePath: string = 'data/nested_dir/sub';
// Setup: Create a directory with a file inside for recursive deletion demo
fs.mkdir(nestedDirToDeletePath, { recursive: true }, (err) => {
if (err && err.code !== 'EEXIST') {
console.error('Error creating nested directory for demo:', err);
return;
}
fs.writeFile(`${nestedDirToDeletePath}/file_inside.txt`, 'Some content', (err) => {
if (err) { console.error('Error creating file inside nested directory:', err); return; }
console.log(`Directory '${nestedDirToDeletePath}' and file created for deletion demo.`);
fs.rm(nestedDirToDeletePath, { recursive: true, force: true }, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error deleting recursive directory '${nestedDirToDeletePath}': ${err.message}`);
return;
}
console.log(`Recursive directory '${nestedDirToDeletePath}' deleted successfully.`);
});
});
});
// Deleting an empty directory
fs.mkdir(dirToDeletePath, (err) => {
if (err && err.code !== 'EEXIST') {
console.error('Error creating empty directory for demo:', err);
return;
}
console.log(`Directory '${dirToDeletePath}' created for deletion demo.`);
fs.rm(dirToDeletePath, { recursive: false }, (err: NodeJS.ErrnoException | null) => {
if (err) {
console.error(`Error deleting empty directory '${dirToDeletePath}': ${err.message}`);
return;
}
console.log(`Empty directory '${dirToDeletePath}' deleted successfully.`);
});
});
PromiseããŒã¹ã®ãã£ã¬ã¯ããªåé€ (`fs/promises`)
import * as fsPromises from 'fs/promises';
async function deleteDirectory(path: string, recursive: boolean = false): Promise
TypeScriptã«ããé«åºŠãªãã¡ã€ã«ã·ã¹ãã æŠå¿µ
åºæ¬çãªèªã¿æžãæäœãè¶ ããŠãNode.jsã¯å€§èŠæš¡ãªãã¡ã€ã«ã®åŠçãé£ç¶çãªããŒã¿ãããŒããã¡ã€ã«ã·ã¹ãã ã®ãªã¢ã«ã¿ã€ã ç£èŠã®ããã®åŒ·åãªæ©èœãæäŸããŸããTypeScriptã®å宣èšã¯ããããã®é«åºŠãªã·ããªãªã«ãåªé ã«æ¡åŒµãããå ç¢æ§ãä¿èšŒããŸãã
ãã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒãšã¹ããªãŒã
éåžžã«å€§èŠæš¡ãªãã¡ã€ã«ã®å Žåãããã¡ã€ã«ã¢ã¯ã»ã¹ïŒäŸïŒãã¡ã€ã«å ã®ç¹å®ã®äœçœ®ïŒããã现ããå¶åŸ¡ããå¿ èŠãããå Žåããã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒãšã¹ããªãŒã ãäžå¯æ¬ ã«ãªããŸããã¹ããªãŒã ã¯ããã¡ã€ã«å šäœãã¡ã¢ãªã«ããŒãããã®ã§ã¯ãªããããŒã¿ããã£ã³ã¯ã§èªã¿æžãããå¹ççãªæ¹æ³ãæäŸããŸããããã¯ãã¹ã±ãŒã©ãã«ãªã¢ããªã±ãŒã·ã§ã³ããäžçäžã®ãµãŒããŒã«ãããå¹ççãªãªãœãŒã¹ç®¡çã«ãšã£ãŠéèŠã§ãã
ãã£ã¹ã¯ãªãã¿ãŒã䜿çšãããã¡ã€ã«ã®ãªãŒãã³ãšã¯ããŒãº (`fs.open`, `fs.close`)
ãã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒã¯ããªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã«ãã£ãŠéããããã¡ã€ã«ã«å²ãåœãŠãããäžæã®èå¥åïŒæ°å€ïŒã§ãã`fs.open`ã䜿çšããŠãã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒãååŸãããã®ãã£ã¹ã¯ãªãã¿ãŒã䜿çšããŠ`fs.read`ã`fs.write`ãªã©ã®æäœãå®è¡ããæåŸã«`fs.close`ããããšãã§ããŸãã
import * as fs from 'fs';
import { promises as fsPromises } from 'fs';
import { constants } from 'fs';
const descriptorFilePath: string = 'data/descriptor_example.txt';
async function demonstrateFileDescriptorOperations(): Promise
ãã¡ã€ã«ã¹ããªãŒã (`fs.createReadStream`, `fs.createWriteStream`)
ã¹ããªãŒã ã¯ãå€§èŠæš¡ãªãã¡ã€ã«ãå¹ççã«åŠçããããã®åŒ·åãªããŒã«ã§ãã`fs.createReadStream`ãš`fs.createWriteStream`ã¯ãããã`Readable`ãš`Writable`ã¹ããªãŒã ãè¿ããNode.jsã®ã¹ããªãŒãã³ã°APIãšã·ãŒã ã¬ã¹ã«çµ±åãããŸããTypeScriptã¯ããããã®ã¹ããªãŒã ã€ãã³ãïŒäŸïŒ`'data'`ã`'end'`ã`'error'`ïŒã«åªããåå®çŸ©ãæäŸããŸãã
import * as fs from 'fs';
const largeFilePath: string = 'data/large_file.txt';
const copiedFilePath: string = 'data/copied_file.txt';
// Create a dummy large file for demonstration
function createLargeFile(path: string, sizeInMB: number): void {
const content: string = 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. '; // 56 chars
const stream = fs.createWriteStream(path);
const totalChars = sizeInMB * 1024 * 1024; // Convert MB to bytes
const iterations = Math.ceil(totalChars / content.length);
for (let i = 0; i < iterations; i++) {
stream.write(content);
}
stream.end(() => console.log(`Created large file '${path}' (${sizeInMB}MB).`));
}
// For demonstration, let's ensure the 'data' directory exists first
fs.mkdir('data', { recursive: true }, (err) => {
if (err && err.code !== 'EEXIST') {
console.error('Error creating data directory:', err);
return;
}
createLargeFile(largeFilePath, 1); // Create a 1MB file
});
// Copy file using streams
function copyFileWithStreams(source: string, destination: string): void {
const readStream = fs.createReadStream(source);
const writeStream = fs.createWriteStream(destination);
readStream.on('open', () => console.log(`Reading stream for '${source}' opened.`));
writeStream.on('open', () => console.log(`Writing stream for '${destination}' opened.`));
// Pipe data from read stream to write stream
readStream.pipe(writeStream);
readStream.on('error', (err: Error) => {
console.error(`Read stream error: ${err.message}`);
});
writeStream.on('error', (err: Error) => {
console.error(`Write stream error: ${err.message}`);
});
writeStream.on('finish', () => {
console.log(`File '${source}' copied to '${destination}' successfully using streams.`);
// Clean up dummy large file after copy
fs.unlink(largeFilePath, (err) => {
if (err) console.error('Error deleting large file:', err);
else console.log(`Large file '${largeFilePath}' deleted.`);
});
});
}
// Wait a bit for the large file to be created before attempting to copy
setTimeout(() => {
copyFileWithStreams(largeFilePath, copiedFilePath);
}, 1000);
倿Žã®ç£èŠ: `fs.watch`, `fs.watchFile`
éçºãµãŒããŒã®ããããªããŒãããã«ãããã»ã¹ããªã¢ã«ã¿ã€ã ã®ããŒã¿åæãªã©ã®ã¿ã¹ã¯ã§ã¯ããã¡ã€ã«ã·ã¹ãã ã®å€æŽãç£èŠããããšãäžå¯æ¬ ã§ããNode.jsã«ã¯ããããè¡ãããã®2ã€ã®äž»èŠãªã¡ãœããããããŸã: `fs.watch`ãš`fs.watchFile`ãTypeScriptã¯ãã€ãã³ãã¿ã€ããšãªã¹ããŒãã©ã¡ãŒã¿ãŒãæ£ããåŠçãããããšãä¿èšŒããŸãã
`fs.watch`: ã€ãã³ãããŒã¹ã®ãã¡ã€ã«ã·ã¹ãã ç£èŠ
`fs.watch`ã¯ãå€ãã®å Žåããªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã¬ãã«ã®éç¥ïŒäŸïŒLinuxã®`inotify`ãmacOSã®`kqueue`ãWindowsã®`ReadDirectoryChangesW`ïŒã䜿çšãããããäžè¬ã«ããå¹ççã§ããç¹å®ã®ãã¡ã€ã«ããã£ã¬ã¯ããªã®å€æŽãåé€ãåå倿Žãç£èŠããã®ã«é©ããŠããŸãã
import * as fs from 'fs';
const watchedFilePath: string = 'data/watched_file.txt';
const watchedDirPath: string = 'data/watched_dir';
// Ensure files/directories exist for watching
fs.writeFileSync(watchedFilePath, 'Initial content.');
fs.mkdirSync(watchedDirPath, { recursive: true });
console.log(`Watching '${watchedFilePath}' for changes...`);
const fileWatcher = fs.watch(watchedFilePath, (eventType: string, filename: string | Buffer | null) => {
const fname = typeof filename === 'string' ? filename : filename?.toString('utf8');
console.log(`File '${fname || 'N/A'}' event: ${eventType}`);
if (eventType === 'change') {
console.log('File content potentially changed.');
}
// In a real application, you might read the file here or trigger a rebuild
});
console.log(`Watching directory '${watchedDirPath}' for changes...`);
const dirWatcher = fs.watch(watchedDirPath, (eventType: string, filename: string | Buffer | null) => {
const fname = typeof filename === 'string' ? filename : filename?.toString('utf8');
console.log(`Directory '${watchedDirPath}' event: ${eventType} on '${fname || 'N/A'}'`);
});
fileWatcher.on('error', (err: Error) => console.error(`File watcher error: ${err.message}`));
dirWatcher.on('error', (err: Error) => console.error(`Directory watcher error: ${err.message}`));
// Simulate changes after a delay
setTimeout(() => {
console.log('\n--- Simulating changes ---');
fs.appendFileSync(watchedFilePath, '\nNew line added.');
fs.writeFileSync(`${watchedDirPath}/new_file.txt`, 'Content.');
fs.unlinkSync(`${watchedDirPath}/new_file.txt`); // Also test deletion
setTimeout(() => {
fileWatcher.close();
dirWatcher.close();
console.log('\nWatchers closed.');
// Clean up temporary files/dirs
fs.unlinkSync(watchedFilePath);
fs.rmSync(watchedDirPath, { recursive: true, force: true });
}, 2000);
}, 1000);
`fs.watch`ã«é¢ããæ³šæ: ãã¹ãŠã®ãã©ãããã©ãŒã ã§ããã¹ãŠã®çš®é¡ã®ã€ãã³ãïŒäŸïŒãã¡ã€ã«åã®å€æŽãåé€ããã³äœæãšããŠå ±åãããå ŽåãããïŒã«å¯ŸããŠåžžã«ä¿¡é Œã§ããããã§ã¯ãããŸãããå ç¢ãªã¯ãã¹ãã©ãããã©ãŒã ã®ãã¡ã€ã«ç£èŠã«ã¯ã`chokidar`ã®ãããªã©ã€ãã©ãªãæ€èšããŠãã ãããããã¯å€ãã®å Žåã`fs.watch`ãå éšã§äœ¿çšããŸãããæ£èŠåãšãã©ãŒã«ããã¯ã¡ã«ããºã ã远å ããŠããŸãã
`fs.watchFile`: ããŒãªã³ã°ããŒã¹ã®ãã¡ã€ã«ç£èŠ
`fs.watchFile`ã¯ãããŒãªã³ã°ïŒãã¡ã€ã«ã®`stat`ããŒã¿ã宿çã«ãã§ãã¯ããïŒã䜿çšããŠå€æŽãæ€åºããŸããå¹çã¯å£ããŸãããç°ãªããã¡ã€ã«ã·ã¹ãã ããããã¯ãŒã¯ãã©ã€ãéã§ããäžè²«æ§ããããŸãã`fs.watch`ãä¿¡é Œã§ããªãç°å¢ïŒäŸïŒNFSå ±æïŒã«ããé©ããŠããŸãã
import * as fs from 'fs';
import { Stats } from 'fs';
const pollFilePath: string = 'data/polled_file.txt';
fs.writeFileSync(pollFilePath, 'Initial polled content.');
console.log(`Polling '${pollFilePath}' for changes...`);
fs.watchFile(pollFilePath, { interval: 1000 }, (curr: Stats, prev: Stats) => {
// TypeScript ensures 'curr' and 'prev' are fs.Stats objects
if (curr.mtimeMs !== prev.mtimeMs) {
console.log(`File '${pollFilePath}' modified (mtime changed). New size: ${curr.size} bytes.`);
}
});
setTimeout(() => {
console.log('\n--- Simulating polled file change ---');
fs.appendFileSync(pollFilePath, '\nAnother line added to polled file.');
setTimeout(() => {
fs.unwatchFile(pollFilePath);
console.log(`\nStopped watching '${pollFilePath}'.`);
fs.unlinkSync(pollFilePath);
}, 2000);
}, 1500);
ã°ããŒãã«ãªã³ã³ããã¹ãã«ããããšã©ãŒåŠçãšãã¹ããã©ã¯ãã£ã¹
ãã¡ã€ã«ã·ã¹ãã ãšå¯Ÿè©±ããããããæ¬çªå¯Ÿå¿ã¢ããªã±ãŒã·ã§ã³ã«ãšã£ãŠãå ç¢ãªãšã©ãŒåŠçã¯æãéèŠã§ãããã¡ã€ã«æäœã¯ãæš©éã®åé¡ããã£ã¹ã¯å®¹éäžè¶³ãšã©ãŒããã¡ã€ã«ãèŠã€ãããªããI/Oãšã©ãŒããããã¯ãŒã¯ã®åé¡ïŒãããã¯ãŒã¯ããŠã³ãããããã©ã€ãã®å ŽåïŒããŸãã¯åæã¢ã¯ã»ã¹ç«¶åãªã©ãæ§ã ãªçç±ã§å€±æããå¯èœæ§ããããŸããTypeScriptã¯åé¢é£ã®åé¡ãææããã®ã«åœ¹ç«ã¡ãŸãããã©ã³ã¿ã€ã ãšã©ãŒã¯äŸç¶ãšããŠæ éãªç®¡çãå¿ èŠã§ãã
ãšã©ãŒåŠçæŠç¥
- åææäœ: `fs.xxxSync`åŒã³åºãã¯åžžã«`try...catch`ãããã¯ã§å²ã¿ãŸãããããã®ã¡ãœããã¯çŽæ¥ãšã©ãŒãã¹ããŒããŸãã
- éåæã³ãŒã«ããã¯: `fs`ã³ãŒã«ããã¯ã®æåã®åŒæ°ã¯åžžã«`err: NodeJS.ErrnoException | null`ã§ããåžžã«ãã®`err`ãªããžã§ã¯ããæåã«ãã§ãã¯ããŠãã ããã
- PromiseããŒã¹ (`fs/promises`): `await`ãšãšãã«`try...catch`ã䜿çšãããã`.then()`ãã§ãŒã³ãšãšãã«`.catch()`ã䜿çšããŠãæåŠãåŠçããŸãã
ãšã©ãŒãã°ã®åœ¢åŒãæšæºåããã¢ããªã±ãŒã·ã§ã³ã®ãšã©ãŒãã£ãŒãããã¯ããŠãŒã¶ãŒåãã§ããå Žåã¯ããšã©ãŒã¡ãã»ãŒãžã®åœéåïŒi18nïŒãæ€èšãããšè¯ãã§ãããã
import * as fs from 'fs';
import { promises as fsPromises } from 'fs';
import * as path from 'path';
const problematicPath = path.join('non_existent_dir', 'file.txt');
// Synchronous error handling
try {
fs.readFileSync(problematicPath, 'utf8');
} catch (error: any) {
console.error(`Sync Error: ${error.code} - ${error.message} (Path: ${problematicPath})`);
}
// Callback-based error handling
fs.readFile(problematicPath, 'utf8', (err, data) => {
if (err) {
console.error(`Callback Error: ${err.code} - ${err.message} (Path: ${problematicPath})`);
return;
}
// ... process data
});
// Promise-based error handling
async function safeReadFile(filePath: string): Promise
ãªãœãŒã¹ç®¡ç: ãã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒã®ã¯ããŒãº
`fs.open`ïŒãŸãã¯`fsPromises.open`ïŒã䜿çšããå Žåããšã©ãŒãçºçããå Žåã§ããæäœå®äºåŸã«`fs.close`ïŒãŸãã¯`fileHandle.close()`ïŒã䜿çšããŠãã¡ã€ã«ãã£ã¹ã¯ãªãã¿ãŒãåžžã«éããããšãéèŠã§ãããããæ ããšããªãœãŒã¹ãªãŒã¯ãçºçãããªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã®ãªãŒãã³ãã¡ã€ã«å¶éã«éããã¢ããªã±ãŒã·ã§ã³ãã¯ã©ãã·ã¥ããããä»ã®ããã»ã¹ã«åœ±é¿ãäžãããããå¯èœæ§ããããŸãã
`FileHandle`ãªããžã§ã¯ãã䜿çšãã`fs/promises` APIã¯ã`fileHandle.close()`ããã®ç®çã®ããã«ç¹å¥ã«èšèšãããŠããã`FileHandle`ã€ã³ã¹ã¿ã³ã¹ã¯`Disposable`ã§ããããïŒNode.js 18.11.0+ããã³TypeScript 5.2+ã䜿çšããŠããå ŽåïŒãéåžžãããç°¡çŽ åããŸãã
ãã¹ç®¡çãšã¯ãã¹ãã©ãããã©ãŒã äºææ§
ãã¡ã€ã«ãã¹ã¯ãªãã¬ãŒãã£ã³ã°ã·ã¹ãã ã«ãã£ãŠå€§ããç°ãªããŸãïŒäŸïŒWindowsã§ã¯`\`ãUnixã©ã€ã¯ãªã·ã¹ãã ã§ã¯`/`ïŒãNode.jsã®`path`ã¢ãžã¥ãŒã«ã¯ãã¯ãã¹ãã©ãããã©ãŒã äºææ§ã®ããæ¹æ³ã§ãã¡ã€ã«ãã¹ãæ§ç¯ããã³è§£æããããã«äžå¯æ¬ ã§ãããã°ããŒãã«å±éã«äžå¯æ¬ ã§ãã
- `path.join(...paths)`: ãã¹ãŠã®äžãããããã¹ã»ã°ã¡ã³ããçµåããçµæã®ãã¹ãæ£èŠåããŸãã
- `path.resolve(...paths)`: ãã¹ãŸãã¯ãã¹ã»ã°ã¡ã³ãã®ã·ãŒã±ã³ã¹ã絶察ãã¹ã«è§£æ±ºããŸãã
- `path.basename(path)`: ãã¹ã®æåŸã®éšåãè¿ããŸãã
- `path.dirname(path)`: ãã¹ã®ãã£ã¬ã¯ããªåãè¿ããŸãã
- `path.extname(path)`: ãã¹ã®æ¡åŒµåãè¿ããŸãã
TypeScriptã¯ã`path`ã¢ãžã¥ãŒã«ã®å®å šãªåå®çŸ©ãæäŸãããã®é¢æ°ãæ£ãã䜿çšããããšãä¿èšŒããŸãã
import * as path from 'path';
const dir = 'my_app_data';
const filename = 'config.json';
// Cross-platform path joining
const fullPath: string = path.join(__dirname, dir, filename);
console.log(`Cross-platform path: ${fullPath}`);
// Get directory name
const dirname: string = path.dirname(fullPath);
console.log(`Directory name: ${dirname}`);
// Get base file name
const basename: string = path.basename(fullPath);
console.log(`Base name: ${basename}`);
// Get file extension
const extname: string = path.extname(fullPath);
console.log(`Extension: ${extname}`);
䞊è¡åŠçãšç«¶åç¶æ
è€æ°ã®éåæãã¡ã€ã«æäœãåæã«éå§ãããå Žåãç¹ã«æžã蟌ã¿ãåé€ã®å Žåãç«¶åç¶æ ãçºçããå¯èœæ§ããããŸããããšãã°ãããæäœããã¡ã€ã«ã®ååšã確èªããå¥ã®æäœãæåã®æäœãå®è¡ãããåã«ãã¡ã€ã«ãåé€ããå Žåãæåã®æäœãäºæãã倱æããå¯èœæ§ããããŸãã
- éèŠãªãã¹ããžãã¯ã«ã¯`fs.existsSync`ãé¿ããŠãã ããã`fs.access`ã䜿çšããããåã«æäœã詊ã¿ãŠãšã©ãŒãåŠçããããšããå§ãããŸãã
- æä»çã¢ã¯ã»ã¹ãå¿ èŠãšããæäœã«ã¯ãé©åãª`flag`ãªãã·ã§ã³ïŒäŸïŒæä»çæžã蟌ã¿ã«ã¯`'wx'`ïŒã䜿çšããŠãã ããã
- éåžžã«éèŠãªå ±æãªãœãŒã¹ã¢ã¯ã»ã¹ã«ã¯ãããã¯ã¡ã«ããºã ïŒäŸïŒãã¡ã€ã«ããã¯ããŸãã¯ã¢ããªã±ãŒã·ã§ã³ã¬ãã«ã®ããã¯ïŒãå®è£ ããŸãããããã«ããè€éããå¢ããŸãã
æš©é (ACL)
ãã¡ã€ã«ã·ã¹ãã æš©éïŒã¢ã¯ã»ã¹å¶åŸ¡ãªã¹ããŸãã¯æšæºUnixæš©éïŒã¯ããšã©ãŒã®äžè¬çãªåå ã§ããNode.jsããã»ã¹ã«ããã¡ã€ã«ããã³ãã£ã¬ã¯ããªã®èªã¿åããæžã蟌ã¿ããŸãã¯å®è¡ã«å¿ èŠãªæš©éãããããšã確èªããŠãã ãããããã¯ãã³ã³ããåãããç°å¢ããããã»ã¹ãç¹å®ã®ãŠãŒã¶ãŒã¢ã«ãŠã³ãã§å®è¡ããããã«ããŠãŒã¶ãŒã·ã¹ãã ã§ç¹ã«éèŠã§ãã
çµè«: ã°ããŒãã«ãã¡ã€ã«ã·ã¹ãã æäœã«ãããåå®å šæ§ã®æ¡çš
Node.jsã®`fs`ã¢ãžã¥ãŒã«ã¯ããã¡ã€ã«ã·ã¹ãã ãšå¯Ÿè©±ããããã®åŒ·åã§æ±çšæ§ã®é«ãããŒã«ã§ãããåºæ¬çãªãã¡ã€ã«æäœããé«åºŠãªã¹ããªãŒã ããŒã¹ã®ããŒã¿åŠçãŸã§ãå¹ åºããªãã·ã§ã³ãæäŸããŸãããããã®æäœã®äžã«TypeScriptãéããããšã§ãã³ã³ãã€ã«æãšã©ãŒæ€åºãã³ãŒãã®æç¢ºæ§ã®åäžãåªããããŒã«ãµããŒãããªãã¡ã¯ã¿ãªã³ã°äžã®èªä¿¡ã®åäžãšãã貎éãªã¡ãªãããåŸãããŸããããã¯ã倿§ãªã³ãŒãããŒã¹å šäœã§äžè²«æ§ãšææ§ãã®è»œæžãäžå¯æ¬ ãªã°ããŒãã«éçºããŒã ã«ãšã£ãŠç¹ã«éèŠã§ãã
å°èŠæš¡ãªãŠãŒãã£ãªãã£ã¹ã¯ãªãããæ§ç¯ããŠããå Žåã§ããå€§èŠæš¡ãªãšã³ã¿ãŒãã©ã€ãºã¢ããªã±ãŒã·ã§ã³ãæ§ç¯ããŠããå Žåã§ããNode.jsãã¡ã€ã«æäœã«TypeScriptã®å ç¢ãªåã·ã¹ãã ãæŽ»çšããããšã§ãããä¿å®ãããããä¿¡é Œæ§ãé«ãããšã©ãŒã«åŒ·ãã³ãŒããäœæãããŸããããã¯ãªãŒã³ãªéåæãã¿ãŒã³ã«ã¯`fs/promises` APIãæ¡çšããåæåŒã³åºããšéåæåŒã³åºãã®ãã¥ã¢ã³ã¹ãçè§£ããåžžã«å ç¢ãªãšã©ãŒåŠçãšã¯ãã¹ãã©ãããã©ãŒã ãã¹ç®¡çãåªå ããŠãã ããã
ãã®ã¬ã€ãã§è°è«ãããååãšäŸãé©çšããããšã§ãäžçäžã®éçºè ã¯ã髿§èœã§å¹ççã§ããã ãã§ãªããæ¬è³ªçã«å®å šã§çè§£ãããããã¡ã€ã«ã·ã¹ãã ã€ã³ã¿ã©ã¯ã·ã§ã³ãæ§ç¯ããæçµçã«ããé«å質ãªãœãããŠã§ã¢ææç©ã«è²¢ç®ã§ããŸãã