Resolving Merge Conflicts - JavaScript

  1. Which replacement correctly resolves the conflict while meeting both requirements?
    Answer: const config = { apiUrl: "/v2", timeout: 5000 }; When resolving a Git merge conflict, your job is to read both versions carefully and manually construct the result that satisfies the stated requirements — Git won't do this for you. The conflict markers tell you exactly what each branch contributed: HEAD (your current branch, main) has apiUrl: "/v2" and timeout: 1000, while feature-timeout has apiUrl: "/v1" and timeout: 5000. The requirements are explicit: keep the API endpoint from main ("/v2") and the timeout from feature-timeout (5000). That means you need to cherry-pick one value from each branch, producing const config = { apiUrl: "/v2", timeout: 5000 }; — which is answer A. Here's why the other options fall short. B (apiUrl: "/v1", timeout: 1000) takes both values from the wrong branch — the API endpoint comes from feature-timeout and the timeout from main, which is the exact opposite of what's required. C (apiUrl: "/v2", timeout: 1000) simply accepts the HEAD/main version unchanged, ignoring the requirement to incorporate the timeout from feature-timeout. D (apiUrl: "/v1", timeout: 5000) accepts the feature-timeout version entirely, discarding main's API endpoint. A useful strategy: before touching any code, annotate each value in the conflict block with its source branch. Then cross-reference those annotations against the requirements one field at a time. This prevents the common trap of accidentally accepting one branch wholesale instead of blending the two intentionally.
  2. Which command sequence applies that decision and marks the file resolved?
    Answer: git checkout --ours -- src/theme.js, followed by git add src/theme.js When resolving a Git merge conflict manually, two concepts must work together correctly: choosing the right version of the file, and properly staging it so Git knows the conflict is resolved. During a merge, --ours refers to the branch you're currently on (the branch receiving the merge), while --theirs refers to the incoming branch being merged in. Since the developer is on main and wants to keep main's version, git checkout --ours -- src/theme.js is the right tool — it overwrites the conflicted file with the exact content from main, discarding the redesign changes entirely. After resolving a conflict by checking out a specific version, Git still sees the file as unresolved unless you explicitly stage it. Running git add src/theme.js tells Git "this conflict is handled," moving the file to the staging area so the merge commit can proceed. This makes D the correct sequence. A fails on both counts: --theirs pulls in the redesign version, which is exactly what the developer wants to discard, and skipping git add means Git never marks the conflict as resolved. B uses --theirs correctly in syntax but picks the wrong version — it keeps redesign's changes rather than main's. C uses --ours correctly to restore the main version, but skipping git add leaves the conflict unresolved in Git's index, so git commit will either fail or complain about unresolved conflicts. A handy memory trick: ours = our current branch. And always remember — after any manual conflict resolution, git add is mandatory before committing.
  3. Which sequence correctly resolves the conflict according to that decision?
    Answer: Restore legacy.js with git checkout --theirs -- legacy.js, then run git add legacy.js. When resolving a Git merge conflict, understanding whose changes you want to keep is everything. The terms --ours and --theirs in git checkout refer to specific branches: --ours means the branch you're currently on (here, main), while --theirs means the branch being merged in (feature-legacy). Since the team decided to keep the *modified file from feature-legacy*, you need to restore that version. Running git checkout --theirs -- legacy.js pulls the file as it exists on feature-legacy, effectively undoing the deletion that main introduced. After restoring the file, you stage it with git add legacy.js to tell Git the conflict is resolved and the file should be included in the merge commit. That's exactly what B does, making it correct. A is wrong because --ours restores the main version — but main deleted legacy.js. Running --ours here would give you nothing (or fail), which is the opposite of what the team wants. C accepts the deletion by running git rm legacy.js, which explicitly tells Git to record the file as removed. This resolves the conflict in favor of main's deletion, directly contradicting the team's decision to keep the file. D is a trap: it correctly uses --theirs to restore the file, but then immediately removes it with git rm, undoing the restore entirely. The two steps cancel each other out. A handy memory trick: --ours = the branch you're on, --theirs = the branch coming in. Always anchor those terms to the merge context before choosing.
  4. Which next action correctly records the resolution and then completes the merge?
    Answer: Stage src/app.js, then run git merge --continue or create the merge commit. Whenever you see a question about resolving a merge conflict in Git, focus on the required sequence: resolve → stage → commit. Git's merge process is paused, waiting for you to signal that a conflict is resolved before it can finalize anything. After manually editing the file and removing conflict markers, Git still sees src/app.js as unmerged because you haven't told Git the conflict is resolved. The way you signal resolution is by staging the file with git add src/app.js. Once staged, the file moves out of "Unmerged paths" and into the staging area. From there, you either run git merge --continue (which automatically creates the merge commit) or run git commit directly. That's exactly what A describes — stage first, then complete the merge — making it the correct sequence. B is backwards. You cannot create the merge commit before staging the resolved file; Git will refuse to commit while unmerged paths still exist. C reverses the required order in a different way — git merge --continue won't succeed if the file hasn't been staged yet, and removing a file from staging afterward would undo your resolution entirely. D is destructive: git reset --hard throws away all your local changes, including the conflict resolution you just carefully performed, and restores the repository to its pre-merge state — the opposite of completing the merge. A useful mental shortcut: resolve → add → continue. Any question showing a paused merge should trigger this sequence in your mind, and if the steps are presented out of order, that answer is wrong.
  5. What is the expected result?
    Answer: Git refuses the commit because src/b.js remains an unmerged path. When working with Git merges, it's critical to understand that Git tracks merge state at the index (staging area) level — a merge is only complete when all conflicts are resolved and staged. Think of it as Git requiring explicit confirmation for every conflicted file before it will finalize a merge commit. Here's what happens in this scenario: after resolving src/a.js and running git add src/a.js, that file moves from "unmerged" to "staged" in Git's index. However, src/b.js still exists in the index as an unmerged path — Git internally stores all three versions (base, ours, theirs) for conflicted files until you resolve them. When you run git commit without addressing src/b.js, Git inspects the index, finds an unmerged path, and refuses the commit, printing an error like error: Committing is not possible because you have unmerged files. That makes C the correct answer. A is wrong because Git never silently picks one branch's version of a conflicted file — resolving conflicts is always an explicit developer action. B is wrong for a similar reason: Git doesn't "omit" conflicted files from a merge commit; every conflicted file must be explicitly resolved and staged. D describes a state that can't exist — Git won't create the merge commit at all while unmerged paths remain, so there's no scenario where the commit succeeds but src/b.js stays conflicted. A useful rule of thumb: run git status before committing during a merge. Any file listed under "Unmerged paths" will block the commit — you must resolve, stage, and then commit.
  6. Which function body is the correct resolution?
    Answer: function label(user) { return formatUserName(user).toUpperCase(); } When you encounter a Git merge conflict, your job isn't to pick one side or the other — it's to synthesize both sets of changes. The conflict markers tell a story: HEAD shows what main currently has, and the incoming branch shows what the feature added. Your resolution must honor both histories simultaneously. Here, main renamed formatName to formatUserName (the old function no longer exists), while the uppercase-label branch added .toUpperCase() to the return value. A correct resolution needs to use the new function name and apply the uppercase transformation. That's exactly what C does — return formatUserName(user).toUpperCase() threads both changes together cleanly. A is wrong because it keeps only the main side, discarding the feature branch's uppercase behavior entirely. You'd be silently losing a deliberate change. B is wrong because it keeps only the feature branch's version, still calling the deleted formatName function — this would cause a runtime error since that helper no longer exists on main. D is the worst of both worlds: it calls the deleted formatName and drops the .toUpperCase() transformation, losing both contributions. A practical tip: when resolving conflicts, mentally label each change with why it was made. Here, one change is a refactor (rename) and the other is a feature addition (uppercase). Refactors and feature additions are usually independent and composable — that's your signal that the correct resolution combines them rather than choosing one. Always verify that your resolved code doesn't reference anything that was deleted on the other branch.
  7. Which files must have their conflicts resolved and staged before Git can complete this merge?
    Answer: Only src/app.js and config/settings.js, because both are listed as unmerged. When Git encounters a merge conflict, it marks affected files as "unmerged" and halts the merge process until those specific conflicts are resolved. Understanding the three sections of git status output is the key to answering this correctly. The Unmerged paths section is the critical one here. Files listed there — src/app.js and config/settings.js — contain conflict markers (<<<<<<<, =======, >>>>>>>) that you must manually resolve, then stage with git add. Only after all unmerged paths are cleared can Git finalize the merge commit. This makes A the correct answer. B is wrong because src/utils.js appearing under "Changes to be committed" means Git has already handled it — it's staged and ready. No further action is needed for that file to complete the merge. C is wrong because it includes README.md, which appears under "Changes not staged for commit." This means it was simply modified in your working directory outside of the merge conflict — perhaps you edited it manually. It is not a merge conflict at all, and Git doesn't require it to be staged before completing the merge. D is wrong because not every modification in git status represents a conflict. Confusing "modified" with "conflict" is a common trap. Git clearly separates these into distinct sections precisely to help you distinguish between them. A good rule of thumb: only files in the Unmerged paths section block a merge. Learn to read git status section by section rather than treating all modifications as equivalent.
  8. Which command is specifically intended for this situation?
    Answer: git merge --abort, which abandons the in-progress merge and restores the pre-merge state When working with Git merges, it helps to think of the workflow in stages: before, during, and after. A merge in progress — one that has produced conflicts but hasn't been committed — is a special intermediate state, and Git provides dedicated commands for managing it cleanly. The command designed exactly for this scenario is git merge --abort (D). When a merge is in progress and you decide you want out entirely, --abort tells Git to stop the merge, discard all conflict markers and partial edits, and restore your working tree and index to the state they were in before the merge command ran. It's a clean escape hatch, built specifically for this workflow. The distractors each represent a different misunderstanding. A (git add .) stages files rather than reverting them — running it mid-conflict would actually mark conflicts as resolved without fixing anything, which could corrupt your commit. It doesn't restore any original state. B (git merge --continue) is the opposite of aborting: it tells Git you've finished resolving all conflicts and are ready to proceed with the merge. Using it before conflicts are actually resolved would either fail or produce a broken commit. C (git restore .) discards working-tree changes to tracked files and can help in some recovery scenarios, but it doesn't understand or exit the merge state itself — the repository would still think a merge is in progress. A useful pattern to remember: Git's --abort flag is consistently used across commands (merge, rebase, cherry-pick) to mean "cancel this operation entirely and go back." When a question describes wanting to fully undo an in-progress operation, --abort is almost always the right instinct.
  9. If the merge commit is then created without staging again, what content is recorded for version.js?
    Answer: The commit records 2.0, while the unstaged working-tree edit still contains 3.0. When working with Git merges, it helps to think of three distinct layers: the repository (last commit), the index/staging area (what git add records), and the working tree (your actual files on disk). A merge commit, like any commit, snapshots exactly what is in the index — not what's in the working tree. Here's the key sequence: after resolving the conflict, the developer ran git add version.js, which wrote the "2.0" content into the index. Then they edited the file again to "3.0", but never ran git add a second time. That second edit lives only in the working tree. When git commit runs, Git reads the index, finds "2.0", and that's what gets permanently recorded. The "3.0" edit remains sitting in the working tree, unstaged and uncommitted — making B the correct answer. A is wrong because it assumes commits snapshot the working tree. They don't — Git commits always snapshot the index. This is one of Git's most commonly misunderstood behaviors. C is wrong because Git has no mechanism to merge or blend staged and unstaged content into a single file version. The index holds one definitive snapshot per file. D is wrong because an unstaged edit after git add doesn't invalidate or undo the conflict resolution already staged. Git won't reintroduce the conflict markers — it simply commits what was staged. The study tip here: whenever you see a Git question involving staging, ask yourself which layer is being read. Commits read the index; the working tree is just a scratch pad until you git add.
  10. What does Git do in this situation?
    Answer: Git can complete the merge because staging marks the text conflict resolved, even though the JavaScript is invalid. When you see a question about Git merge resolution, focus on what Git actually tracks versus what it leaves to you. Git's job during a merge conflict is to detect text-level conflicts — places where both branches modified the same lines. Once you remove the conflict markers (<<<<<<<, =======, >>>>>>>) and stage the file, Git considers its part done. It has no idea whether the resulting file is valid JavaScript, Python, or even gibberish — it only cares that the conflict markers are gone and the file is staged. That's why A is correct. Staging a previously-conflicted file signals to Git that you have resolved the conflict. git merge --continue then finalizes the merge commit without inspecting file syntax. The JavaScript error is your problem, not Git's. B is wrong because Git does not parse or compile source code at any point. It treats all files as blobs of bytes. There is no built-in JavaScript validator in Git's merge process (syntax checking would require a commit hook, which the question explicitly rules out). C is wrong because Git won't retroactively re-insert conflict markers. Once you remove them and stage the file, Git trusts your judgment. It has no mechanism to detect "invalid" code choices since it doesn't understand code semantics. D is wrong because Git never silently substitutes file content behind your back during a merge. That would undermine the entire purpose of manual conflict resolution. The key study tip here: Git is a content tracker, not a code validator. Staging = resolved, in Git's view. Always run your tests after resolving conflicts — Git won't catch runtime or syntax errors for you.

Start this quiz