1. 为什么要把文件夹传到 GitHub?先弄懂核心思路
很多人在接触 GitHub 之前,可能只是在网上下载过开源软件,或者看过别人分享的项目链接。等到自己手里有一个完整的项目文件夹,想把它传到 GitHub 上托管、备份、给同学评审或者发布成开源项目时,才发现操作起来比想象中麻烦。尤其是文件夹里文件一多,网页端拖拽上传经常中途断掉,命令行又不知道该敲什么,很容易卡在第一步。
这篇分享就是围绕“上传文件夹到 GitHub”这件事,把网页端和命令行两种方式都拆开讲清楚。我会尽量按照一步步配图的思路,把每个操作节点、每条命令的含义、每一个容易踩坑的地方都说明白。不管你是第一次接触 Git 的纯新手,还是之前只会在网页上点来点去、想补上命令行这块短板的开发者,这篇内容都可以直接拿来参考。
先说核心结论:如果文件夹里文件数量不多(比如几十个以内),用网页端拖拽上传最快;如果文件夹结构复杂、文件数量多、之后还要持续更新,那就老老实实用 Git 命令行。两种方式不冲突,甚至组合使用很常见——平时用命令行提交,偶尔在网页端改一行配置或传一个小文件。
1.1 网页拖拽和命令行到底选哪个
很多人上来就会问:GitHub 网页上不是也有 Upload files 按钮吗?为什么还要学 Git 命令?
这个问题的答案,取决于你“上传文件夹”这个动作是一次性的,还是长久的。网页端上传的本质是一个手动把文件搬运到仓库的过程:你打开仓库页面,点 Upload files,然后把文件拖进网页。听起来挺方便,但一旦文件多、体积大,或者文件夹嵌套多层,网页端就开始力不从心。浏览器上传断掉一次、网络抖动一下,整个流程就要重来。而且网页端默认不会保留你本地的 Git 提交历史,如果本地已经有项目演进过程,这些记录就丢了。
命令行上传则完全不一样。它背后是 Git 这套版本管理工具在工作:本地所有文件先被 Git 记录下来,形成一个一个提交(commit),然后一次性推送到 GitHub。这就像你在本地写日记,Git 帮你把每一天的记录归档好,网络好的时候一起寄出去;网页端则像是你手动一份一份复印邮寄,简单但很笨重。
所以我的建议是分场景:一次性分享、文件少,可以网页端拖拽;文件多、结构复杂、将来还要继续改,必须先学会命令行。这篇文章会把两种方式都讲透,你按自己的情况选就行。
1.2 一个比喻理解 Git 和 GitHub 的关系
很多教程上来就教你敲命令,却不解释为什么要有这套东西。我习惯用一个比喻:Git 是你的本地“时光机+备份系统”,GitHub 是你的“云端共享仓库”。
你在本地建好一个文件夹,Git 可以让这个文件夹的每一个阶段变化都被记录成一个快照。你改了一行代码,保存一次;过几天又改了一行,再保存一次。每一次保存就是一次 commit。这些 commit 都留在你本地,完全不需要网络。而 GitHub 是一个远程仓库,当你想把本地这些快照同步到云端,让同事看到、让别的电脑拉取,或者单纯防止电脑硬盘坏了,就用 git push 把本地记录推送上去。
所以“上传文件夹到 GitHub”这个过程,用行话说其实是:把本地文件夹初始化成 Git 仓库 → 提交一次版本快照 → 关联到 GitHub 上的远程仓库 → 把自己本地的快照推送上去。理解了这个流程,后面所有命令都是在执行这几个动作。怕就怕不了解全貌的人,敲完 git init 就不知道下一步干嘛,或者 push 的时候报错也不知道去哪查。
2. 动手前的环境准备
任何实操类教程,环境出问题都会让后面的步骤全部白费。所以我把准备阶段单独拿出来说,不想让环境问题成为劝退原因。
2.1 注册账号与安装 Git 客户端
GitHub 账号的注册这里不展开,去官网首页就能看到注册入口,用邮箱注册、验证一下邮箱就行。注册好之后,要记住你的用户名,因为后续远程仓库地址里会用到。
本地则需要安装 Git 客户端。Windows 用户去 Git 官网下载对应版本,安装的时候一路默认选项即可;macOS 用户装了 Homebrew 的话可以 brew install git,也可以直接下载官方安装包。安装完成后,在终端或命令行里输入 git --version,能看到版本号说明安装成功。
这一步容易出问题的是:Windows 用户安装完 Git 之后,进入 Git Bash 还是命令提示符里操作?我的经验是统一用 Git Bash,它模拟了 Linux 终端环境,路径解析、命令兼容性都更好,也方便后续使用常见的 Unix 命令。如果在 cmd 或者 PowerShell 里操作,部分命令的写法或路径分隔符会有差异,容易让新手困惑。
2.2 配置身份信息(名字和邮箱)
Git 在每次提交时都会记录一个作者信息,这个信息就来自你本地的全局配置。第一次安装完 Git 后,必须设置一下,否则提交时可能会报错,或者提交记录里显示的不是你想展示的名字。
打开终端,分别执行:
git config --global user.name "你的GitHub用户名" git config --global user.email "你的注册邮箱"这里有一个细节:Git 本地配置的身份信息,最好和 GitHub 账号保持一致。这样推送出去后,提交记录上的作者信息才正确对应到你的账号。如果你在本机同时处理多个项目,想对某个项目单独设置不同身份,可以去掉 --global,在项目目录内重新执行一次配置,作用范围就变成只对当前仓库生效了。
2.3 SSH 密钥配置(免密推送的关键)
第一次推送时,很多人的第二道坎就是认证问题。GitHub 提供了两种常见认证方式:HTTPS 和 SSH。
HTTPS 方式最简单,推送时输入 GitHub 的用户名和密码(现在更常用的是 Personal Access Token,简称 PAT)即可,不需要额外配置;缺点是每次推送都要输凭据,配置了凭据管理器才能免密。SSH 方式则是通过密钥对进行身份认证:本地生成一对私钥和公钥,公钥放到 GitHub 账号的 SSH Keys 设置里,之后 push 和 pull 都不用再输密码,一劳永逸。
我推荐大家用 SSH 方式。生成密钥的命令是:
ssh-keygen -t ed25519 -C "你的注册邮箱"一路回车即可。生成后,使用 cat ~/.ssh/id_ed25519.pub 查看公钥内容,复制它,然后到 GitHub 页面右上角头像 → Settings → SSH and GPG keys → New SSH key,粘贴保存。最后验证:
ssh -T git@github.com如果显示 Hi 你的用户名! You've successfully authenticated...,说明 SSH 已经通了。
提示:如果你在生成密钥时设置了 passphrase,每次使用私钥时还会要求输入。图省事可以留空,安全性要求高的话设置一个也不算坏事。我日常个人项目都留空,公司电脑按公司规定来。
3. 用命令行上传文件夹(详细实操)
环境准备完成后,就可以正式操作了。这部分会从创建本地仓库开始,一步步走到成功推送到 GitHub。中间涉及几条核心命令,每条我都会解释含义,而不仅仅是让你照着输入。
3.1 第一步:初始化本地仓库并提交
假设你本地有一个文件夹叫 my-project,里面是你准备好的项目文件。先在终端里进入这个文件夹:
cd /path/to/my-project然后在项目根目录里初始化 Git 仓库:
git init执行后,项目目录下会多出一个隐藏的 .git 文件夹(Windows 下默认隐藏,需要在文件管理器里开启“显示隐藏项目”才能看到)。这个 .git 文件夹就是 Git 的本地数据库,里面记录着所有版本快照和配置信息。这时候你可以先看一眼当前项目里有哪些文件:
git status这个命令会列出所有未跟踪的文件和改动。初次使用的人常常忽略这一步,直接 commit,结果把一些不该提交的临时文件也提交上去了。所以建议养成习惯,git status 能帮你先确认状态。
如果有不想提交的文件,比如本地开发产生的临时文件、日志、编译产物、密钥等,就要在项目根目录创建一个 .gitignore 文件,把需要忽略的内容写进去。比如:
node_modules/ dist/ *.log .env这个文件可以说是 Git 项目里的“安检名单”,写到里面的路径和规则都会被 Git 自动忽略。没有 .gitignore 的项目,传到 GitHub 上往往带一堆垃圾文件,别人看着头疼,自己也容易传错。
确认要提交的文件没问题后,先把它们加入暂存区:
git add .这条命令把当前目录下所有未忽略的文件都加入暂存区。如果只想提交某个具体文件,可以用 git add 文件名。暂存区这个东西,你可以理解为一个“待打包区”——文件先放到这里,确认无误后再统一打包成一个 commit。
接着提交:
git commit -m "第一次提交项目文件"双引号里的内容是本次提交的说明。命名建议写清楚这次改了什么,方便以后回看。首次提交我一般喜欢写成 init project 或 项目初始化,简明扼要。
到这里,本地仓库已经建立完成,文件也完成了第一次版本快照。
3.2 第二步:创建远程仓库并关联
本地搞定了,接下来在 GitHub 上创建一个空的远程仓库。
登录 GitHub,点击页面右上角的 + 号,选择 New repository。仓库名建议和本地文件夹名保持一致,方便识别。描述可以随便写,选 Public 还是 Private 按你的需求来——想公开分享给所有人看就选 Public,只想自己或协作者看到就选 Private。
有一个关键点:初始化仓库的页面会问你是否要添加 README、.gitignore 或 license。如果你打算先把本地文件夹推上来,这些都不要勾选,保持空仓库状态,否则后续容易遇到本地和远程历史不一致的问题。
创建完毕后,GitHub 会显示一个页面,里面有几段代码,其中包含远程仓库地址。这时候回到本地终端,把远程仓库关联到本地:
git remote add origin git@github.com:你的用户名/仓库名.git如果你想用 HTTPS 方式,地址就是 https://github.com/你的用户名/仓库名.git。用哪个取决于你前面配置的是 SSH 还是 HTTPS 凭据。SSH 方式推荐使用上面的 git@ 开头地址。
关联完可以用 git remote -v 查看当前仓库关联了哪些远程地址。看到两条记录(fetch 和 push),说明关联成功。
3.3 第三步:推送本地代码到远程
远程仓库关联好了,现在做真正的“上传”动作:
git push -u origin main这里有一个高频坑:很多教程里写的是 git push -u origin master,其中 master 是旧版 Git 的默认分支名。而 GitHub 在 2020 年后把新仓库默认分支名改成了 main。你的本地仓库在 git init 后,默认分支名取决于你 Git 客户端配置或版本,可能是 master,也可能是 main。如果不确定,先看:
git branch命令行会显示当前所在分支。如果你的本地分支是 master,但 GitHub 仓库默认分支是 main,直接推送时可能出错。解决方式很简单:推之前先把本地分支改名,执行:
git branch -M main这条命令把当前分支重命名为 main。-M 是大写的 M,表示强制重命名,即使目标分支已存在也会覆盖。改完再执行推送:
git push -u origin main-u 参数的意思是“记住本次推送对应的远程分支”,以后你只需要 git push 就能直接推送,不必每次写完整分支名。第一次推送成功后,回到 GitHub 仓库页面刷新,就能看到文件夹里的所有文件都传上去了。
3.4 后续更新项目怎么推送
上传一次文件夹只是开始。项目是活的,过几天你又改了代码、加了文档,想同步到 GitHub。这时候流程比第一次简单很多,不需要再初始化、再关联远程,只需要三步:
git add . git commit -m "这次改了什么" git push很简单,对吧?git add 把改动放入暂存区,git commit 生成一次新快照,git push 把快照同步到远程。很多教程会把“使用 Git 管理项目”包装得很复杂,其实日常高频操作就是这三条命令。
需要注意的一点:git add . 会把当前项目目录下所有有变动的文件都加进去,如果只想提交部分文件,请改成 git add 具体路径。提交信息也尽量描述清楚,因为 commit 记录会长期保留在仓库历史里,写得太随意,过几个月你自己都看不懂当初改了什么。
4. 网页端直接上传文件夹(适合小批量场景)
如果只是临时想传一个文件夹,里面文件不多、体积不大,直接走网页端会更快。这种方式不用装 Git,不用敲命令,浏览器打开就能操作。
4.1 网页端创建仓库并上传文件
网页端上传的前提是先有一个仓库。如果你还没建,按上一节的方法创建一个空仓库,然后进入仓库页面,点击 Add file → Upload files,就会进入拖拽上传页面。
这时候,你可以把整个文件夹直接拖进浏览器的上传区域。GitHub 会自动遍历文件夹里的所有文件,并保留文件夹层级结构。拖进去之后,页面底部会要求你写一条提交信息(默认是 Add files via upload),可以改成一个更清晰的文件描述。最后点击 Commit changes,上传就完成了。
这个流程看起来很轻松,但有几个限制需要提前知道:网站对单次上传文件大小有限制,单文件超过 100MB 会直接失败(实际上我建议超过 50MB 就别用网页端了);上传过程依赖网络稳定性,中途断网会全部重来;另外网页端也不支持拖拽上传空文件夹,因为 Git 本身不跟踪空目录。
4.2 网页端如何建文件夹(文件名加斜杠)
很多人不知道,网页端加文件时,文件名里如果带了斜杠 /,GitHub 会自动认为这个文件放在对应的子目录里,从而实现直接新建文件夹的效果。比如我要在仓库里建一个 docs 文件夹,里面放一个 README.md,只需要在文件名输入框里写:
docs/README.mdGitHub 会在提交时自动创建 docs 这个目录结构。这个技巧在没有本地环境、只想快速整理仓库目录结构时非常实用。不过它也确实有局限:一次只能建一条路径,如果目录层级特别深,操作起来繁琐;而且无法直接创建空文件夹,必须放至少一个文件占位。常见的做法是先在文件夹里放一个 README.md 或 .gitkeep 文件,让目录被 Git 跟踪。
4.3 网页端上传的限制与取舍
网页端上传毕竟不是一个为“大规模代码托管”设计的路径。文件多了以后,上传列表会有很多行,每传一个文件都会发起一次请求,浏览器可能卡顿甚至崩溃。而且网页端没有办法处理文件名冲突、覆盖更新、历史记录保留这类精细控制。
我见过不少朋友用网页端传文件,传完当时觉得很顺利,等到改了一个文件想再更新时,发现只能把整个文件重新上传一遍,仓库里还留着旧文件。相比之下,命令行方式天然就处理了“变更”而不是“重新上传”这件事,所以日常维护项目,命令行才是正路。
所以在我的实践里,网页端的定位是“应急工具”:临时补一个 README、改一行错误配置、传一两张图片,这时候效率是比命令行高的。但如果是一个文件夹、一个项目打包上传,请用命令行方式完成。两者组合使用,才是效率最高的状态。
5. 常见问题与排查技巧
上传文件夹这件事,动作本身不难,难的是遇到报错不知道怎么处理。我把自己这几年实际操作中高频踩坑的问题整理成一个速查表,遇到问题可以按图索骥。
5.1 高频报错对照表
| 报错信息 | 出现原因 | 解决方式 |
|---|---|---|
| fatal: not a git repository | 当前目录不是 Git 仓库 | 确认是否执行过 git init,是否在正确的项目目录里 |
| error: src refspec main does not match any | 本地没有 main 分支或没有提交过任何内容 | 先执行 git add . 和 git commit,再推送 |
| failed to push some refs | 远程有本地没有的提交记录 | 先 git pull --rebase origin main,再 push |
| repository not found | 远程仓库地址写错或没有权限 | 检查仓库名、用户名是否一致,确认是否 Private 仓库 |
| Permission denied (publickey) | SSH 密钥未配置或公钥未添加到 GitHub | 重新检查 ssh-keygen 生成的公钥,确认添加到 GitHub 设置里 |
| remote origin already exists | 已经关联过远程仓库 | 先 git remote remove origin,再重新关联 |
| unable to access ... SSL certificate problem | 本机网络或 Git 配置异常 | 检查网络环境;如果公司内网有特殊设置,咨询网管或更新 Git 版本 |
这套速查表覆盖了纯新手上路时 90% 的报错场景。遇到报错先别慌,把关键错误信息复制出来,在表格里找一找,大多数都能定位到原因。
5.2 每次都要输密码?文件太大?这些坑提前避开
使用 HTTPS 方式推送时,第一次会让你输入用户名和密码,但现在已经不能用账号密码直接认证了,而要用 Personal Access Token(PAT)。如果你发现密码输进去报错,大概率就是没换成 token。生成 PAT 的路径是 Settings → Developer settings → Personal access tokens → Tokens (classic) → Generate new token,生成时勾选 repo 权限,然后把生成的字符串当密码用。注意这个 token 只显示一次,一定要复制保存。
另一个高频问题是大文件。GitHub 对单文件有 100MB 的硬限制,而仓库整体体积也不适合做得太大。如果你项目里有超过 50MB 的文件(比如模型文件、数据集、视频素材),强烈不建议直接推到普通 Git 仓库。Git 对大文件的处理效率极低,仓库体积膨胀后,每次 clone 和 fetch 都会变慢,团队成员体验也很差。这种情况应该用 Git LFS(Large File Storage)或者换用其他对象存储服务,把大文件单独托管。Git LFS 的接入方式不复杂,安装插件后在项目里用 git lfs track "*.zip" 之类的命令声明哪些文件走 LFS 即可。
还有一个很多人容易忽略的点:文件名大小写。Git 默认情况下不区分文件名大小写变化,比如你本地把 README.md 改成 readme.md,推上去后在 GitHub 上可能仍然显示旧名字。解决方法是 git config core.ignorecase false 或执行 git mv 强制改名。这个问题在团队协作时尤其容易引发混乱,因为不同操作系统对大小写的处理方式不一致。
5.3 让仓库保持整洁的几个习惯
项目传上去只是起点,仓库能不能保持清爽,靠的是日常习惯。我这里分享几个自己坚持了很久的原则。
第一,凡是生成物都不进仓库。编译产物、依赖包、日志文件、IDE 配置文件这些,全部写进 .gitignore。别人 clone 项目后,自己重新安装依赖、编译生成即可,仓库里只保留源代码和必要配置。这样仓库体积小、对比清晰,review 起来也轻松。
第二,提交粒度要小。不要攒了一个月的改动一次性 commit,那样提交信息根本没法起。理想状态是一次提交对应一个完整的小功能或一次 bug 修复,提交信息里说清楚“做了什么”和“为什么做”。这个习惯在出问题时特别有用,回溯排查时会轻松得多。
第三,推送前先看 git status。我见过太多人闭着眼睛 git add . 然后 push,结果把 .env 密钥文件推到了公开仓库,过了一个小时才有人提醒。养成推送前 git status 确认一遍的好习惯,能避开很多无法挽回的泄露事故。
最后再分享一个小技巧
上传完整个文件夹之后,很多人不知道还有一个常用组合:在 GitHub 仓库页面按一下句号键(英文状态下的 .),浏览器会直接打开一个在线版的代码编辑器,你可以在网页上直接修改文件、新建文件,甚至执行 Git 操作。配合之前讲的“文件名加斜杠建目录”技巧,基本能覆盖所有应急场景。再配合命令行推送日常代码,整个工作流就非常顺了。
我个人在实际操作中的体会是:上传文件夹到 GitHub,真正难的从来不是命令,而是理解 Git 的工作流。一旦你明白了本地提交和远程仓库的关系,后面所有命令都只是不同场景下的重复组合。按这篇文章的方式先把第一个文件夹传上去,再跑通一次日常更新,剩下的就是在使用中慢慢加深理解了。