Forked from 0xkhan/push-only-dist-folder-to-liver-server.md
Created
November 14, 2022 17:50
Revisions
-
0xkhan revised this gist
Sep 22, 2022 . 2 changed files with 155 additions and 1 deletion.There are no files selected for viewing
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 charactersOriginal file line number Diff line number Diff line change @@ -1 +0,0 @@ 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 charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,155 @@ # Push Only `dist/` Folder To Live Server I have googled many things and explored many questions on Stack Overflow to find the best way to push only `dist/` directory to live server. I couldn't find any good solution but one person on Stackoverflow suggested to look at Git Submodules and this is the best solution I could come up with. I have never heard of submodules before because almost nobody uses them. If you never heard of it too then I'll first explain what a submodule is and then I'll show you how you can use submodules to push only `dist/` directory to a live server. ### What is a Submodule? A submodule is a repository inside another repository. Basically a project within a project. For example we have a set of dependencies that we need for more than one project. We can put all those dependencies in a repo and add that repo as a submodule in each project. So we bring that repo into our project repo, it lives there and we have access to the whole repository. ### Why and when would you use it? The best example for when you should use submodules is sharing libraries. Other example might be when you have a repository and some files are used across multiple technologies what you can do is to add it as a submodule across all technologies that way every technology will have it available. ### So how do you add a submodule? Let's suppose we have two repos `MyRepo` and `MySubRepo`. `MyRepo` is our working repo, our project and `MySubRepo` is our submodule. Both are separate independent repositories. Now to add a submodule into your working repository Git has a command for it: ```shell git submodule add <url> ``` In our case we wanna go inside `MyRepo/` and run the following command: ```shell /MyRepo$ git submodule add https://github.com/<username>/MySubRepo ``` Now `MySubRepo` is added as a submodule to our working repo `MyRepo`. If `MyRepo` had only `README.md` file it will now have `MySubRepo` as well: ```shell /MyRepo$ ls README.md .gitmodules MySubRepo ``` The `.gitmodules` is the file that keeps track of submodules. Next we wanna add the new added files and push them to our remote respository. ```shell /MyRepo$ git status new file: .gitmodules new file: MySubRepo /MyRepo$ git add . /MyRepo$ git commit -m "Add submodule" /MyRepo$ git push ``` The life cycle of submodules works differently from our standard repository. By default when we use git commands it will ignore all submodules unless we explicitly tell it. So basically if you do `git clone` it will ignore submodules also if you do `git push` or `git branch` it will also by default ignore submodules. To explicitly tell it to focus on submodule we can use `--recurse-submodules` flag e.g: ``` git pull --recurse-submodules # For cloning a repo git clone <url> --recurse-submodules ``` If you forgot to use the `--recurse-submodules` flag you can alternatively use the following command after the repository is cloned: ``` git submodule update --init ``` If we go inside `MySubRepo` you will see that it's on a different branch and that's because we are in a different repository. You can manually checkout to master branch by running `git checkout master`. ### How it works with changes If we make changes to `MySubRepo/README.md` file and push the changes it will update `MySubRepo` repository but when we go back to `MyRepo` we can see that the branch is dirty that means there are changes. It will look like following: ```shell /MyRepo$ git status On branch master Your branch is up to date with 'origin/master'. Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: MySubRepo (new commits) no changes added to commit (use "git add" and/or "git commit -a") ``` As it shows above the main repo is up to date but there were changes in our submodule that needs to be committed. Those changes are not actually changes in our main repo but it's the last commit hash inside our submodule. What that means is that the submodule is updated to a newer version and that specific commit has to be realised and committed inside our main repo. When we do that our submodule will point to the last commit. To update those changes in our working repo we do the following: ```shell /MyRepo$ git add . /MyRepo$ git commit -m "Update submodule version" /MyRepo$ git push ``` Now those changes are also committed and both repos are up to date. ### How to use submodules to only deploy your `dist/` directory to live server > :warning: Disclaimer! This is how I use submodules to deploy only `dist/` directory to live server. Other developer might use other methods e.g distribution branch etc. #### I use the following steps * Create a working repo which is the main project repo * Add your distribution folder as submodule. I name my submodule as `<project name>-dist` * Create your build. The build process has to be done carefully I use `npm` and `Webpack` so the auto-generated `dist/` directory is always there. Do NOT use your `dist/` directory or your submodule as distribution output in webpack because each time you make a build it'll wipe everything out inculding git files. Git files gone means your directory is not a repository anymore, therefore not a submodule. * Commit and push the changes in submodule * Go back to your main repo and commit the hash #### How do I make a build? My way of making a build is that I run `npm run build` and it takes care of everything. My build command first bundles everything and then copy the files from `dist/` directory to `<project name>-dist/` directory. This way only the changes are detected in submodule those changes can then be committed and pushed. Build command in my `package.json`: ``` "scripts": { "devServer": "webpack serve", "watch": "webpack -w", "bundle": "webpack", "copy": "cp -r dist/* <project name>-dist/", "start": "npm-run-all --parallel devServer watch", "build": "npm-run-all bundle copy" } ``` `npm-run-all` is a npm package that helps you run multiple commands when you do `npm run <your command>`. Of course you wanna ignore your `dist/` folder as you ignore `node_modules` etc. You only push `src/` in main Repo and your distribution is added as submodule so it's an independent repo which is only used for deployment. To see how it looks check [this repo](https://github.com/0xkhan/encite-website) out. It's just a static website which is deployed from a submodule. You'll not be able to see the submodule because it's a private repo. Yes, you can use a private repo as submodule. I hope the information is presented clearly. If you have any questions or suggestions then comment them below! -
0xkhan created this gist
Sep 18, 2022 .There are no files selected for viewing
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 charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1 @@ # Git Submodules