From 7f923b2433936ec344a67458f46c9e19b8c1757b Mon Sep 17 00:00:00 2001 From: Keigo Okamoto <107530622+hyphen-o@users.noreply.github.com> Date: Wed, 2 Oct 2024 14:59:38 +0900 Subject: [PATCH] =?UTF-8?q?blob=E3=83=A2=E3=83=87=E3=83=AB=E3=81=AE?= =?UTF-8?q?=E5=AE=9F=E8=A3=85=20(#3)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * git logコマンドの追加 * messageの取得方法の修正 * コマンドの修正 * log.tsの修正 * commitをクラス化 * コマンド入力時の待ち時間短縮 * blobモデルの作成 * compress-buffer.tsの削除 * addコマンドの追加 * eslintの修正 * package.json & eslintの修正 * package.json & readmeの修正 * レビュー後修正 * ハッシュからパスを生成する処理を共通化 * contentをバイナリデータのまま圧縮するように修正 --- README.md | 5 +++++ eslint.config.js | 11 +++++++++- package.json | 2 ++ src/commands/add.ts | 23 ++++++++++++++++++++ src/commands/index.ts | 2 ++ src/commands/log.ts | 2 +- src/functions/colored-log.ts | 12 ++++++----- src/functions/generate-object-path.ts | 17 +++++++++++++++ src/models/blob-object.ts | 31 +++++++++++++++++++++++++++ src/mygit.ts | 4 +++- 10 files changed, 101 insertions(+), 8 deletions(-) create mode 100644 src/commands/add.ts create mode 100644 src/functions/generate-object-path.ts create mode 100644 src/models/blob-object.ts diff --git a/README.md b/README.md index 850e919..8bdb524 100644 --- a/README.md +++ b/README.md @@ -40,6 +40,11 @@ npm run lint:fix # run the formatter npm run format:check npm run format:fix + +# run all check or fix +npm run check +npm run fix + ``` ## publish the package diff --git a/eslint.config.js b/eslint.config.js index 7c759fb..6a856a5 100644 --- a/eslint.config.js +++ b/eslint.config.js @@ -36,7 +36,12 @@ export default [ allowExpressions: true, }, ], - "@typescript-eslint/no-unused-vars": "error", + "@typescript-eslint/no-unused-vars": [ + "warn", + { + argsIgnorePattern: "^_", + }, + ], "@typescript-eslint/array-type": [ "error", { @@ -61,6 +66,10 @@ export default [ { files: ["**/*.js", "**/*.mjs"], ...eslint.configs.recommended, + //追加でルールを指定 + rules: { + "no-unused-vars": ["error", { argsIgnorePattern: "^_.*$" }], + }, languageOptions: { sourceType: "module", globals: { diff --git a/package.json b/package.json index 040f445..a669789 100644 --- a/package.json +++ b/package.json @@ -13,6 +13,8 @@ "lint:fix": "eslint --fix .", "format:check": "prettier --check .", "format:fix": "prettier --write .", + "check": "npm run format:check && npm run lint:check", + "fix": "npm run format:fix && npm run lint:fix", "build": "tsc", "watch": "tsc --watch" }, diff --git a/src/commands/add.ts b/src/commands/add.ts new file mode 100644 index 0000000..785ddb6 --- /dev/null +++ b/src/commands/add.ts @@ -0,0 +1,23 @@ +import { readFileSync } from "node:fs"; + +import { coloredLog } from "../functions/colored-log.js"; +import { BlobObject } from "../models/blob-object.js"; + +export const add = (options: Array): void => { + const filePath = options[0]; + + //引数にファイルパスが含まれていなかった場合の処理 + if (!filePath) { + console.log("Nothing specified, nothing added."); + coloredLog({ + text: "hint: Maybe you wanted to say 'git add XXX'?", + color: "yellow", + }); + return; + } + + const content = readFileSync(filePath); + + const blobObject = new BlobObject(content); + blobObject.dumpBlobObject(); +}; diff --git a/src/commands/index.ts b/src/commands/index.ts index c441b5f..634fcae 100644 --- a/src/commands/index.ts +++ b/src/commands/index.ts @@ -1,6 +1,8 @@ +import { add } from "./add.js"; import { log } from "./log.js"; export const validCommand = { + add: add, log: log, help: () => { console.log("Available commands:"); diff --git a/src/commands/log.ts b/src/commands/log.ts index 2ab33e1..2c86fca 100644 --- a/src/commands/log.ts +++ b/src/commands/log.ts @@ -57,7 +57,7 @@ export const displayCommitHistory = ( }); }; -export const log = (): void => { +export const log = (_options?: Array): void => { const headHash = extractHeadHash(); if (!headHash) { diff --git a/src/functions/colored-log.ts b/src/functions/colored-log.ts index 006b3c2..87b75cf 100644 --- a/src/functions/colored-log.ts +++ b/src/functions/colored-log.ts @@ -1,15 +1,17 @@ +const colors = { + //https://qiita.com/shuhei/items/a61b4324fd5dbc1af79b + yellow: "\u001b[33m", + red: "\u001b[31m", +}; + export const coloredLog = ({ text, color, }: { text: string; - color?: "yellow"; + color?: keyof typeof colors; }): void => { const RESET = "\u001b[0m"; - const colors = { - //https://qiita.com/shuhei/items/a61b4324fd5dbc1af79b - yellow: "\u001b[33m", - }; if (color && color in colors) { console.log(colors[color] + text + RESET); diff --git a/src/functions/generate-object-path.ts b/src/functions/generate-object-path.ts new file mode 100644 index 0000000..c10c077 --- /dev/null +++ b/src/functions/generate-object-path.ts @@ -0,0 +1,17 @@ +import { join } from "node:path"; + +import { GIT_OBJECTS } from "../constants.js"; + +export const generateObjectPath = ( + hash: string, +): { + dirPath: string; + filePath: string; +} => { + const dirPath = join(GIT_OBJECTS, hash.slice(0, 2)); + const filePath = join(GIT_OBJECTS, hash.slice(0, 2), hash.slice(2)); + return { + dirPath, + filePath, + }; +}; diff --git a/src/models/blob-object.ts b/src/models/blob-object.ts new file mode 100644 index 0000000..7d61275 --- /dev/null +++ b/src/models/blob-object.ts @@ -0,0 +1,31 @@ +import { createHash } from "node:crypto"; +import { existsSync, mkdirSync, writeFileSync } from "node:fs"; +import { deflateSync } from "node:zlib"; + +import { generateObjectPath } from "../functions/generate-object-path.js"; + +export class BlobObject { + constructor(private readonly content: Buffer) {} + + public dumpBlobObject = (): void => { + const header = Buffer.from(`blob ${this.content.length.toString()}\x00`); + const store = Buffer.concat([ + Uint8Array.from(header), + Uint8Array.from(this.content), + ]); + + //16進数表示のため,hexに変換 + const hash = createHash("sha1") + .update(Uint8Array.from(store)) + .digest("hex"); + + const { dirPath, filePath } = generateObjectPath(hash); + const compressedBlobObject = deflateSync(Uint8Array.from(store)); + + if (existsSync(filePath)) return; + + if (!existsSync(dirPath)) mkdirSync(dirPath); + + writeFileSync(filePath, Uint8Array.from(compressedBlobObject)); + }; +} diff --git a/src/mygit.ts b/src/mygit.ts index 8afbb49..f5b8bb2 100644 --- a/src/mygit.ts +++ b/src/mygit.ts @@ -15,7 +15,9 @@ export const mygit = async (argv: Array): Promise => { : undefined; if (runCommand) { - runCommand(); + const options = argv.slice(3); + + runCommand(options); } else { console.log(`mygit: '${command}' is not a valid mygit command.\n`); validCommand.help();