Last active
February 9, 2022 07:12
-
-
Save lsongdev/a41ffef47048f097e85088b39e63d476 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// https://kushagra.dev/blog/build-git-learn-git/ | |
function Git(name) { | |
this.name = name; | |
this.lastCommitId = -1; | |
this.branches = []; | |
const master = new Branch("master", null); | |
this.branches.push(master); | |
this.HEAD = master; | |
} | |
Git.prototype.commit = function (message) { | |
const commit = new Commit(++this.lastCommitId, this.HEAD.commit, message); | |
this.HEAD.commit = commit; | |
return commit; | |
}; | |
Git.prototype.log = function () { | |
const history = []; | |
let { commit } = this.HEAD; | |
while (commit) { | |
history.push(commit); | |
commit = commit.parent; | |
} | |
return history; | |
} | |
Git.prototype.checkout = function (branchName) { | |
// Loop through all branches and see if we have a branch | |
// called `branchName`. | |
for (const branch of this.branches) { | |
if (branch.name === branchName) { | |
console.log("Switched to existing branch: " + branchName); | |
this.HEAD = branch | |
return branch; | |
} | |
} | |
// If branch was not found, create a new one. | |
const newBranch = new Branch(branchName, this.HEAD.commit); | |
this.branches.push(newBranch); | |
this.HEAD = newBranch; | |
console.log("Switched to new branch: " + branchName); | |
return newBranch; | |
}; | |
function Commit(id, parent, message) { | |
this.id = id; | |
this.parent = parent; | |
this.message = message; | |
} | |
function Branch(name, commit) { | |
this.name = name; | |
this.commit = commit; | |
} | |
// Maps the array of commits into a string of commit ids. | |
// For [C2, C1,C3], it returns "2-1-0" | |
function historyToIdMapper(history) { | |
var ids = history.map(function(commit) { | |
return commit.id; | |
}); | |
return ids.join("-"); | |
} | |
var repo = new Git("test"); | |
repo.commit("Initial commit"); | |
repo.commit("Change 1"); | |
console.assert(historyToIdMapper(repo.log()) === "1-0"); // Should show 2 commits. | |
repo.checkout("testing"); | |
repo.commit("Change 3"); | |
console.assert(historyToIdMapper(repo.log()) === "2-1-0"); // Should show 3 commits. | |
repo.checkout("master"); | |
console.assert(historyToIdMapper(repo.log()) === "1-0"); // Should show 2 commits. Master unpolluted. | |
repo.commit("Change 3"); | |
console.assert(historyToIdMapper(repo.log()) === "3-1-0"); // Continue on master with 4th commit. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment