sourcecontrol
Version:
A modern TypeScript CLI application for source control
105 lines • 4.08 kB
JavaScript
Object.defineProperty(exports, "__esModule", { value: true });
exports.FileObjectStore = void 0;
const exceptions_1 = require("../exceptions");
const utils_1 = require("../../utils");
const objects_1 = require("../objects");
class FileObjectStore {
constructor() {
this.objectsPath = null;
}
async initialize(gitDir) {
this.objectsPath = gitDir.resolve('objects');
try {
await utils_1.FileUtils.createDirectories(this.objectsPath.fullpath());
}
catch (error) {
throw new exceptions_1.ObjectException('Failed to initialize object store');
}
}
async writeObject(object) {
try {
const serialized = object.serialize();
const sha = await utils_1.HashUtils.sha1Hex(serialized);
const filePath = this.resolveObjectPath(sha);
if (await utils_1.FileUtils.exists(filePath.fullpath())) {
return sha;
}
const compressed = await utils_1.CompressionUtils.compress(serialized);
await utils_1.FileUtils.createDirectories(filePath.parent.fullpath());
await utils_1.FileUtils.createFile(filePath.fullpath(), compressed);
return sha;
}
catch (error) {
throw new exceptions_1.ObjectException('Failed to write object');
}
}
async readObject(sha) {
if (!sha || sha.length < 3) {
return null;
}
try {
const filePath = this.resolveObjectPath(sha);
if (!(await utils_1.FileUtils.exists(filePath.fullpath()))) {
return null;
}
const compressed = await utils_1.FileUtils.readFile(filePath.fullpath());
const decompressed = await utils_1.CompressionUtils.decompress(compressed);
const object = this.createObjectFromHeader(decompressed);
await object.deserialize(decompressed);
return object;
}
catch (error) {
throw new exceptions_1.ObjectException(`Failed to read object: ${sha}`);
}
}
async hasObject(sha) {
if (!sha || sha.length < 3) {
return false;
}
const filePath = this.resolveObjectPath(sha);
return await utils_1.FileUtils.exists(filePath.fullpath());
}
resolveObjectPath(sha) {
if (!this.objectsPath) {
throw new exceptions_1.ObjectException('Object store not initialized');
}
const dirName = sha.substring(0, 2);
const fileName = sha.substring(2);
const dirPath = this.objectsPath.resolve(dirName);
return dirPath.resolve(fileName);
}
createObjectFromHeader(data) {
let nullIndex = -1;
for (let i = 0; i < data.length; i++) {
if (data[i] == 0) {
nullIndex = i;
break;
}
}
if (nullIndex == -1) {
throw new exceptions_1.ObjectException('Invalid object format: no null terminator');
}
const header = new TextDecoder().decode(data.slice(0, nullIndex));
const parts = header.split(' ');
if (parts.length != 2) {
throw new exceptions_1.ObjectException('Invalid object header format');
}
const type = parts[0];
const objectType = objects_1.ObjectTypeHelper.fromString(type);
switch (objectType) {
case objects_1.ObjectType.BLOB:
return new objects_1.BlobObject();
case objects_1.ObjectType.TREE:
return new objects_1.TreeObject();
case objects_1.ObjectType.COMMIT:
return new objects_1.CommitObject();
case objects_1.ObjectType.TAG:
throw new exceptions_1.ObjectException('Tag objects not yet implemented');
default:
throw new exceptions_1.ObjectException('Unknown object type: ' + type);
}
}
}
exports.FileObjectStore = FileObjectStore;
//# sourceMappingURL=file-object-store.js.map
;