Git manages local version history, GitHub provides hosting, collaboration, and a web interface, and
ghaccesses GitHub from the terminal. This article establishes the boundaries between the three without repeating the internals of Git objects, commit graphs, or rebase.
GitHub does not replace Git. Everyday collaboration usually involves three layers: creating commits locally with Git, storing and displaying repositories remotely on GitHub, and, when useful, using the official GitHub CLI (gh) to work with repositories, issues, pull requests (PRs), and Actions. For the details of Git remote synchronization, see Git 03: remote collaboration.
1. The roles of Git, GitHub, and gh#
| Component | What it is | Typical questions | Common entry points |
|---|---|---|---|
| Git | A local distributed version control tool | How do I commit, switch branches, merge, and synchronize? | git status、git switch、git commit |
| GitHub | A collaboration platform that hosts Git repositories | Where does the code live? Who can view, review, and merge it? | Repository web pages, Issues, Pull requests, Actions |
gh |
The official GitHub command-line client | How do I work with GitHub objects from the terminal? | gh auth、gh repo、gh issue、gh pr、gh run |
One easily confused boundary: git push sends Git commits to a remote address; it does not itself know about issues or PRs. gh pr create creates a PR on GitHub, targeting a base branch in a GitHub repository.
Another boundary: Git can create commits and branches without a network connection. GitHub repositories, permissions, issues, PRs, and Actions require access to the GitHub service. gh is a client for GitHub APIs and web-related functionality, not a replacement for Git.
2. Authentication and gh auth#
2.1 Choose a Git transport protocol
The common protocols for reading and writing GitHub repositories from a local machine are HTTPS (for example, https://github.com/OWNER/REPO.git, with sign-in handled by a credential helper) and SSH (for example, git@github.com:OWNER/REPO.git, requiring a registered public key and testable with ssh -T git@github.com). Both support clone, fetch, and push. The protocol does not determine repository permissions; those depend on the account, visibility, collaborator roles, and branch rules.
2.2 Sign in with gh
First confirm that the client is installed, then start interactive sign-in:
gh --version
gh auth login
gh auth statusgh auth login asks you to choose a GitHub host and Git protocol, and usually opens a browser to complete authorization. gh auth status checks the current host and account status. Do not paste its full output or any credentials into public issues, logs, or notes.
If you are already signed in but Git operations still cannot write, you can have gh configure a credential helper for Git:
gh auth setup-gitAuthentication safety boundaries: do not put personal access tokens (PATs), SSH private keys, GH_TOKEN, GITHUB_TOKEN, or remote URLs containing credentials in repositories, scripts, shell history, .git/config, or logs. Automation tokens belong in GitHub Secrets or the restricted contexts provided by Actions. Do not run or forward commands that print tokens directly.
Authentication establishes who you are and whether you can gain access; it does not mean you can push to any repository. If you encounter permission denied, first confirm the remote address and signed-in account, then check repository permissions or use a fork workflow.
Official documentation: gh auth login, gh auth.
3. Create, clone, and fork repositories#
3.1 Create your own repository
The web navigation may change with GitHub’s UI. Typically, use + → New repository in the top-right corner, then choose the owner, name, visibility, and initial files before creating it. Organizations may restrict repository creation. Empty repositories and repositories initialized with a README also show different instructions for the first clone/push.
You can also use gh:
gh repo create my-project --private
gh repo create my-project --public --clone--private and --public are important visibility choices; do not publish a repository containing private material just to test the workflow. --clone clones the repository locally after successful creation. To create a remote repository from an existing local directory, use --source and --push, but first inspect the commits and files you will publish.
Official documentation: Creating a new repository, gh repo create.
3.2 Clone, fork, and branch are different operations
| Operation | Location | Result | When to use it |
|---|---|---|---|
clone |
GitHub repository → local machine | A local copy of a Git repository | To start examining or modifying a remote repository |
fork |
GitHub repository → your GitHub account | A separate server-side repository that retains its relationship to the upstream project | To prepare a contribution when you cannot write to the original repository |
branch |
Local Git repository (can also be pushed to a remote) | A development line branching from a commit | To isolate a feature, fix, or experiment |
Forking a repository therefore does not automatically download the code to your computer, and cloning one does not automatically create a repository under your GitHub account. Contributors commonly fork first, clone their fork, and then create a local feature branch.
3.3 Clone locally
Native Git command:
git clone https://github.com/OWNER/REPO.git
cd REPOA clone retrieves all Git data currently visible from the remote repository, not just the files displayed on the website. A shallow clone with git clone --depth 1 ... can save time and space, but omits history. You may need to fetch that missing history later to compare older commits, switch to historical branches, or generate certain version information.
After cloning, use git status --short --branch, git remote -v, and git branch --show-current to inspect the working directory, remote addresses, and current branch. These commands do not establish that the current account has write permission.
3.4 Two remotes after forking: origin and upstream
Remote names are local conventions, not reserved GitHub words:
originusually points to the remote repository you are working with. In a fork workflow, that is usually the fork under your account, to which you can push.upstreamusually points to the original project repository so you can obtain the original authors’ new commits. You can usually only fetch from it; whether you can push depends on your permissions.
If you cloned your own fork, origin may already point to it. In that case, just add the upstream remote:
git remote add upstream https://github.com/OWNER/REPO.git
git remote -vDo not assume that the names origin or upstream are always correct. What matters is using git remote -v to confirm the URL behind each name. gh repo clone may automatically add upstream for a fork; the client version and options affect this behavior. Verify it with git remote -v.
Official documentation: Cloning a repository, gh repo clone, gh repo fork.
4. The boundaries between fetch, pull, and push#
These three commands all involve a remote, but have different side effects:
| Command | What it does | Does it directly change current working files? |
|---|---|---|
git fetch <remote> |
Downloads remote objects and updates remote-tracking branches | Usually leaves the current branch and working files unchanged |
git pull <remote> <branch> |
Fetches first, then integrates the result into the current branch | Integrates commits and may cause conflicts |
git push <remote> <branch> |
Sends local commits to a remote branch | Leaves local working files unchanged, but changes remote state |
4.1 Inspect first, then integrate
git fetch upstream
git log --oneline --decorate HEAD..upstream/mainHEAD..upstream/main denotes commits present in the remote branch but absent from the current branch. This inspects differences; it does not merge them. The actual default branch may be named master or something else. Replace main with the default branch shown by the repository first.
If the current branch has no uncommitted changes and you want to integrate remote updates into the local branch, you can use:
git pull --rebase origin mainpull --rebase does not guarantee a conflict-free result; it can still pause and require conflict resolution. Follow team conventions before rebasing a shared branch, because rebase rewrites the ancestry of local commits. To inspect the process in two steps, use git fetch, then explicitly run git rebase or git merge after checking.
4.2 First push and its risks
After confirming the current branch, commits to be pushed, and remote address, push a new branch for the first time:
git push --set-upstream origin feature/short-description--set-upstream establishes the relationship between the local branch and its remote-tracking branch, allowing you to use git pull and git push directly afterward. git push exposes commits to people with access to that remote; it does not automatically create a PR.
Do not treat git push --force as an ordinary retry. It can move the remote branch pointer and make commits already pushed by others temporarily unreachable from that branch. Consider the following only after confirming that you alone use the branch, understanding the effects of rewriting history, and obtaining your team’s permission:
git push --force-with-lease origin feature/short-description--force-with-lease refuses to overwrite the remote when its state does not match local expectations, adding a safeguard beyond --force. It is still not a routine operation for a public branch.
5. Navigating repository pages, issues, PRs, and Actions#
Tabs and buttons on GitHub’s website change. The descriptions below focus on their stable meanings; use the controls currently shown in the repository when working.
5.1 Repository home and code access
- Code: obtain HTTPS/SSH clone URLs and browse files and branches.
- Issues: record bugs, tasks, questions, and feature ideas. An issue is an object for discussion and tracking, not a Git commit.
- Pull requests: compare a head branch with a base branch, then review, check, and merge the changes.
- Settings: manage visibility, collaborators, branch rules, Secrets, and more. Appropriate permissions are required.
- Actions: view workflows, runs, logs, and failed steps. A repository may disable Actions or restrict which workflows can run.
From the terminal, use these commands to open or inspect the relevant pages:
gh repo view --web
gh issue list
gh pr list
gh run list
gh run view5.2 How issues, pull requests, and Actions fit together
A common collaboration sequence is:
- Describe the problem, expected behavior, reproduction steps, or task boundaries in an issue.
- Create a local branch, change the code, and commit.
- Push the branch to a remote where you have write access.
- Create a PR from the head branch to the target repository’s base branch.
- GitHub Actions runs checks on push or PR events; maintainers inspect the diff, comments, and check results.
- After review and required checks pass, merge the PR according to repository rules.
Issues and PRs can be linked with keywords such as Fixes #123. Whether merging automatically closes an issue depends on the target repository and how the issue is referenced. Actions is an event-driven automation platform. For this article, it is enough to know that events such as PRs and pushes produce checks. Workflows, jobs, runners, permissions, and caching are covered in later notes in the GitHub series.
Official resources: Issues, Pull requests, Understanding GitHub Actions.
6. Complete command workflow: fork, push, then create a PR#
The following assumes that OWNER/REPO is the original repository, YOUR_USER is your GitHub login, and the original repository’s default branch is main. Replace the placeholders in the variables first. These variables do not contain passwords or tokens.
6.1 Create a fork and prepare the remotes
UPSTREAM_OWNER="OWNER"
REPO="REPO"
YOUR_USER="YOUR_USER"
gh auth status
gh repo fork "$UPSTREAM_OWNER/$REPO" --clone=false
git clone "https://github.com/$YOUR_USER/$REPO.git" "$REPO"
cd "$REPO"
git remote add upstream "https://github.com/$UPSTREAM_OWNER/$REPO.git"
git remote -vIf the fork already exists, skip gh repo fork and clone the existing fork directly. If your team prefers SSH, replace both HTTPS URLs with their SSH equivalents; do not add tokens to URLs.
6.2 Create a development branch from the upstream default branch
git fetch upstream
git switch -c fix/short-description upstream/mainIf the original repository’s default branch is not main, replace main in the commands with its actual name. git switch -c creates and switches to a local branch; it does not publish the branch on GitHub.
6.3 Inspect, commit, and push
After editing files, use explicit paths to inspect and stage changes:
git status --short
git diff --check
git diff
git add -- path/to/changed-file
git diff --cached --check
git commit -m "Fix the short problem description"
git push --set-upstream origin HEADgit add -- path/to/changed-file makes it easier than an unconditional git add . to avoid committing .env, build outputs, editor caches, or unrelated files. git push origin HEAD pushes the current branch, reducing the chance of mistyping its name. It still publishes the commit, so check git remote -v before running it.
6.4 Create a pull request
gh pr create \
--base main \
--head "$YOUR_USER:fix/short-description" \
--fillYou can also open the newly pushed branch on GitHub and choose Compare & pull request. When creating a PR, confirm that base is the original repository and its target branch, while head is your fork and its feature branch. Reversing them can create the PR in the wrong repository or compare the wrong branches.
After creation, inspect it with:
gh pr status
gh pr checks
gh run listWait for Actions checks, respond to review comments, and update the branch according to repository rules. For further changes, keep committing and pushing on the same feature branch; the existing PR updates automatically. Do not create another PR for every small fix.
7. Common misconceptions and safety checks#
Common misconceptions can be reduced to four checks:
- A fork is not a branch: a fork is a remote copy under an account; a branch is a development line in the commit graph. The former addresses where to push, and the latter how to isolate changes.
origindoes not mean the official repository: it is simply the default local remote name. In a fork workflow it usually refers to your fork, while the original project is namedupstream.pulldoes more than download:fetchonly updates remote-tracking information, whilepullalso integrates changes into the current branch and may cause conflicts. To inspect first, start withfetch.- Pushing does not create a PR: a push updates a remote branch. A PR must be created explicitly through the website or
gh pr create. Running CI is not the same as requesting a merge.
Before each fetch/push, run:
git remote -vConfirm the URL before performing a write operation. Do not hard-code the assumption that every repository has main, or infer push access from the ability to clone. First confirm the default branch, fork owner, remote URL, and account. Branch protection may additionally require a PR, reviews, or mandatory checks.
Credentials and private files
If you find tokens, private keys, .env, or personal data, stop before pushing. Remove exposed credentials and rotate them, then follow the repository’s security procedure. A later commit that deletes a file does not erase it from history. Once sensitive information has been pushed, treat it as leaked.
Official documentation#
- GitHub Docs: creating and managing repositories, Cloning a repository
- GitHub Docs: Issues, Pull requests, Understanding GitHub Actions
- GitHub CLI Manual、
gh auth login、gh repo clone、gh repo fork - Official Git documentation,
git-clone,git-fetch,git-pull,git-push
References & further reading
- gh auth login ↗
- gh auth ↗
- Creating a new repository ↗
- gh repo create ↗
- Cloning a repository ↗
- gh repo clone ↗
- gh repo fork ↗
- Issues ↗
- Pull requests ↗
- Understanding GitHub Actions ↗
- GitHub Docs: creating and managing repositories ↗
- GitHub CLI Manual ↗
- Official Git documentation ↗
- git-clone ↗
- git-fetch ↗
- git-pull ↗
- git-push ↗
Adapted from technical notes. Examples use generic names.