├── images ├── gitignore │ ├── img.png │ ├── img_1.png │ ├── img_2.png │ ├── img_3.png │ ├── img_4.png │ ├── img_5.png │ ├── img_6.png │ ├── img_7.png │ └── github-gitignore.png ├── readme │ └── gitgithub.png ├── create_git_project │ ├── img_add.png │ ├── img_init.png │ ├── github_new.png │ ├── img_checkout.png │ ├── img_commit.png │ ├── img_status.png │ ├── img_github_ssh.png │ ├── github-push-error.png │ ├── img_change_commit.png │ ├── img_checkout_main.png │ ├── img_commit_email.png │ ├── img_git_history.png │ ├── img_git_modified.png │ ├── img_git_success.png │ ├── img_modify_readme.png │ ├── img_push_success.png │ ├── img_github_add_ssh.png │ ├── img_create_project_github.png │ └── img_github_repository_info.png ├── remove-rename-files │ ├── rm_git.png │ ├── push_rm.png │ ├── rm_file.png │ ├── rename_file.png │ ├── rm-add-file.png │ ├── commit-rename.png │ ├── mv-git-style.png │ ├── rm-git-style.png │ ├── add_hello_world.png │ ├── rename-add-file.png │ ├── push-mv-git-style.png │ └── push-rm-git-style.png └── developing_a_project_from_different_machines │ ├── merge_pull.png │ ├── pull_output.png │ ├── pull_reject.png │ ├── pull_result.png │ ├── error_message.png │ ├── github_names.png │ ├── names_rebase.png │ ├── cloning_options.png │ ├── cloning_output.png │ ├── commits-history.png │ ├── git-commit-push.png │ ├── merge_conflict.png │ ├── merge_final_push.png │ ├── names_txt_file.png │ ├── commits_on_github.png │ ├── new_name_main_repo.png │ ├── resolved_conflict.png │ ├── continue_rebase_push.png │ ├── merge_names_conflict.png │ ├── merge_reject_message.png │ ├── github_after_conflicts.png │ ├── primary_commit_history.png │ ├── second_machine_changes.png │ ├── merge_resolved_conflicts.png │ ├── primary_repo_commit_history.png │ └── rebase_git_status_git_branch.png ├── LICENSE ├── .gitignore ├── gitignore.md ├── removing-renaming-files.md ├── Readme.md ├── creating_git_project.md └── developing_a_project_from_different_machines.md /images/gitignore/img.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img.png -------------------------------------------------------------------------------- /images/gitignore/img_1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_1.png -------------------------------------------------------------------------------- /images/gitignore/img_2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_2.png -------------------------------------------------------------------------------- /images/gitignore/img_3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_3.png -------------------------------------------------------------------------------- /images/gitignore/img_4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_4.png -------------------------------------------------------------------------------- /images/gitignore/img_5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_5.png -------------------------------------------------------------------------------- /images/gitignore/img_6.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_6.png -------------------------------------------------------------------------------- /images/gitignore/img_7.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/img_7.png -------------------------------------------------------------------------------- /images/readme/gitgithub.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/readme/gitgithub.png -------------------------------------------------------------------------------- /images/create_git_project/img_add.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_add.png -------------------------------------------------------------------------------- /images/gitignore/github-gitignore.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/gitignore/github-gitignore.png -------------------------------------------------------------------------------- /images/remove-rename-files/rm_git.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rm_git.png -------------------------------------------------------------------------------- /images/create_git_project/img_init.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_init.png -------------------------------------------------------------------------------- /images/remove-rename-files/push_rm.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/push_rm.png -------------------------------------------------------------------------------- /images/remove-rename-files/rm_file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rm_file.png -------------------------------------------------------------------------------- /images/create_git_project/github_new.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/github_new.png -------------------------------------------------------------------------------- /images/create_git_project/img_checkout.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_checkout.png -------------------------------------------------------------------------------- /images/create_git_project/img_commit.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_commit.png -------------------------------------------------------------------------------- /images/create_git_project/img_status.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_status.png -------------------------------------------------------------------------------- /images/remove-rename-files/rename_file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rename_file.png -------------------------------------------------------------------------------- /images/remove-rename-files/rm-add-file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rm-add-file.png -------------------------------------------------------------------------------- /images/create_git_project/img_github_ssh.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_github_ssh.png -------------------------------------------------------------------------------- /images/remove-rename-files/commit-rename.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/commit-rename.png -------------------------------------------------------------------------------- /images/remove-rename-files/mv-git-style.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/mv-git-style.png -------------------------------------------------------------------------------- /images/remove-rename-files/rm-git-style.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rm-git-style.png -------------------------------------------------------------------------------- /images/create_git_project/github-push-error.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/github-push-error.png -------------------------------------------------------------------------------- /images/create_git_project/img_change_commit.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_change_commit.png -------------------------------------------------------------------------------- /images/create_git_project/img_checkout_main.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_checkout_main.png -------------------------------------------------------------------------------- /images/create_git_project/img_commit_email.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_commit_email.png -------------------------------------------------------------------------------- /images/create_git_project/img_git_history.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_git_history.png -------------------------------------------------------------------------------- /images/create_git_project/img_git_modified.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_git_modified.png -------------------------------------------------------------------------------- /images/create_git_project/img_git_success.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_git_success.png -------------------------------------------------------------------------------- /images/create_git_project/img_modify_readme.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_modify_readme.png -------------------------------------------------------------------------------- /images/create_git_project/img_push_success.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_push_success.png -------------------------------------------------------------------------------- /images/remove-rename-files/add_hello_world.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/add_hello_world.png -------------------------------------------------------------------------------- /images/remove-rename-files/rename-add-file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/rename-add-file.png -------------------------------------------------------------------------------- /images/create_git_project/img_github_add_ssh.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_github_add_ssh.png -------------------------------------------------------------------------------- /images/remove-rename-files/push-mv-git-style.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/push-mv-git-style.png -------------------------------------------------------------------------------- /images/remove-rename-files/push-rm-git-style.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/remove-rename-files/push-rm-git-style.png -------------------------------------------------------------------------------- /images/create_git_project/img_create_project_github.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_create_project_github.png -------------------------------------------------------------------------------- /images/create_git_project/img_github_repository_info.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/create_git_project/img_github_repository_info.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_pull.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_pull.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/pull_output.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/pull_output.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/pull_reject.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/pull_reject.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/pull_result.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/pull_result.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/error_message.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/error_message.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/github_names.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/github_names.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/names_rebase.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/names_rebase.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/cloning_options.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/cloning_options.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/cloning_output.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/cloning_output.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/commits-history.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/commits-history.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/git-commit-push.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/git-commit-push.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_conflict.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_conflict.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_final_push.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_final_push.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/names_txt_file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/names_txt_file.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/commits_on_github.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/commits_on_github.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/new_name_main_repo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/new_name_main_repo.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/resolved_conflict.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/resolved_conflict.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/continue_rebase_push.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/continue_rebase_push.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_names_conflict.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_names_conflict.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_reject_message.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_reject_message.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/github_after_conflicts.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/github_after_conflicts.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/primary_commit_history.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/primary_commit_history.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/second_machine_changes.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/second_machine_changes.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/merge_resolved_conflicts.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/merge_resolved_conflicts.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/primary_repo_commit_history.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/primary_repo_commit_history.png -------------------------------------------------------------------------------- /images/developing_a_project_from_different_machines/rebase_git_status_git_branch.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/pooya-mohammadi/intro_to_git/HEAD/images/developing_a_project_from_different_machines/rebase_git_status_git_branch.png -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 Pooya Mohammadi Kazaj 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Distribution / packaging 10 | .Python 11 | build/ 12 | develop-eggs/ 13 | dist/ 14 | downloads/ 15 | eggs/ 16 | .eggs/ 17 | lib/ 18 | lib64/ 19 | parts/ 20 | sdist/ 21 | var/ 22 | wheels/ 23 | pip-wheel-metadata/ 24 | share/python-wheels/ 25 | *.egg-info/ 26 | .installed.cfg 27 | *.egg 28 | MANIFEST 29 | 30 | # PyInstaller 31 | # Usually these files are written by a python script from a template 32 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 33 | *.manifest 34 | *.spec 35 | 36 | # Installer logs 37 | pip-log.txt 38 | pip-delete-this-directory.txt 39 | 40 | # Unit test / coverage reports 41 | htmlcov/ 42 | .tox/ 43 | .nox/ 44 | .coverage 45 | .coverage.* 46 | .cache 47 | nosetests.xml 48 | coverage.xml 49 | *.cover 50 | *.py,cover 51 | .hypothesis/ 52 | .pytest_cache/ 53 | 54 | # Translations 55 | *.mo 56 | *.pot 57 | 58 | # Django stuff: 59 | *.log 60 | local_settings.py 61 | db.sqlite3 62 | db.sqlite3-journal 63 | 64 | # Flask stuff: 65 | instance/ 66 | .webassets-cache 67 | 68 | # Scrapy stuff: 69 | .scrapy 70 | 71 | # Sphinx documentation 72 | docs/_build/ 73 | 74 | # PyBuilder 75 | target/ 76 | 77 | # Jupyter Notebook 78 | .ipynb_checkpoints 79 | 80 | # IPython 81 | profile_default/ 82 | ipython_config.py 83 | 84 | # pyenv 85 | .python-version 86 | 87 | # pipenv 88 | # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. 89 | # However, in case of collaboration, if having platform-specific dependencies or dependencies 90 | # having no cross-platform support, pipenv may install dependencies that don't work, or not 91 | # install all needed dependencies. 92 | #Pipfile.lock 93 | 94 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow 95 | __pypackages__/ 96 | 97 | # Celery stuff 98 | celerybeat-schedule 99 | celerybeat.pid 100 | 101 | # SageMath parsed files 102 | *.sage.py 103 | 104 | # Environments 105 | .env 106 | .venv 107 | env/ 108 | venv/ 109 | ENV/ 110 | env.bak/ 111 | venv.bak/ 112 | 113 | # Spyder project settings 114 | .spyderproject 115 | .spyproject 116 | 117 | # Rope project settings 118 | .ropeproject 119 | 120 | # mkdocs documentation 121 | /site 122 | 123 | # mypy 124 | .mypy_cache/ 125 | .dmypy.json 126 | dmypy.json 127 | 128 | # Pyre type checker 129 | .pyre/ 130 | 131 | .idea 132 | *__pycache__* 133 | -------------------------------------------------------------------------------- /gitignore.md: -------------------------------------------------------------------------------- 1 | # How to ignore files and directories from unintentionally being committed 2 | 3 | While working on a project, you may have some files or directories that you do not want them to be committed. 4 | There are several reasons that you might not want to add some files to your repository: 5 | 1) A huge dataset file 6 | 2) Private files, like passwords and tokens 7 | 3) system or application specific files/configurations, like `.idea` for `pycharm` and `.ipynb_checkpoints` 8 | 4) ... 9 | 10 | 11 | ## Table of Contents 12 | 1. [Simulating a use case for gitignore](#simulating-a-use-case-for-gitignore) 13 | 2. [How to add .gitignore at the time of project creation in GitHub](#how-to-add-gitignore-at-the-time-of-project-creation-in-github) 14 | 3. [How to create .gitignore for various use cases](#how-to-create-gitignore-for-various-use-cases) 15 | 16 | 17 | ## Simulating a use case for gitignore 18 | To make sure that these unwanted files will not unintentionally be committed, you should append your files 19 | and directories' paths to a file called `.gitignore`. This file is recognized by `git`, and whenever a file's 20 | name appears in it, the `git`, simply, ignores it and does not even show in the output of the `status` command. 21 | 22 | For the sake of this project, consider that we have a directory that contains a text file including some passwords. 23 | To make it more realistic, imagine that you are working in a team and these passwords are unique for each developer. 24 | Therefore, by committing this file you may overwrite others passwords our reveal yours, which both of them should be 25 | avoided! 26 | 27 | 28 | So, first let's create a folder with a text file in linux:
29 | ``` 30 | cd git_01 31 | mkdir credentials 32 | cd credentials 33 | cat >> credentials.txt 34 | username: pooya-mohammadi 35 | password: ************** 36 | ``` 37 | ![img.png](images/gitignore/img.png) 38 | 39 | **Note**: If you are Windows user, simply graphically create a directory including a text file containing the following 40 | text or what ever text you desire:) 41 | ``` 42 | username: pooya-mohammadi 43 | password: ************** 44 | ``` 45 | 46 | Let's see the output of the `git status` command:
47 | ![img.png](images/gitignore/img_7.png) 48 | 49 | As you can see, the `git` itself is suggesting you to commit the file. If you have several files to commit, the chances 50 | are that you may commit `credentials` along the others by mistake. 51 | 52 | ### Create a .gitignore file 53 | ``` 54 | touch .gitignore # If you are on Windows, create a new and empty text file graphically and rename it to .gitignore 55 | cat >> .gitignore 56 | credentials/ 57 | cat >> .gitignore 58 | git status 59 | ``` 60 | **Note**: create an empty text file in windows 61 | 62 | ![img_2.png](images/gitignore/img_2.png) 63 | ![img_1.png](images/gitignore/img_1.png) 64 | 65 | **Image Notes:** 66 | 1) make sure the spelling of `.gitignore` is correct! 67 | 2) If you are a Windows user, create a text file with no `.txt` extension, open the file as a `txt` file, and type `credentials/` in it. 68 | 3) The `.gitignore` file is recognized by the `git` and the suggestion for committing `credentials` directory is removed. 69 | 70 | ### Add the .gitignore file, so everyone can benefit from it 71 | ```gitignore 72 | git add .gitignore 73 | git commit -m "Add credentials directory to gitignore" 74 | git push origin main 75 | git status 76 | ``` 77 | ![img_3.png](images/gitignore/img_3.png) 78 | 79 | Done! With this, everyone can benefit from this file! 80 | 81 | ## How to add .gitignore at the time of project creation in GitHub 82 | GitHub offers various templates for `.gitignore`. These templates are mainly based on various programing languages: 83 | 84 | ![img_3.png](images/gitignore/github-gitignore.png) 85 | ![img_4.png](images/gitignore/img_4.png) 86 | 87 | After creating your project `.gitignore` will be created automatically. 88 | ![img_5.png](images/gitignore/img_5.png) 89 | 90 | **Image Notes:** 91 | 1) I choose gitignore to be created for `python` programing language 92 | 2) There are several files specific to `python` that should not be included in projects' repositories because they system specific, like __pycache__, etc. 93 | 94 | 95 | ## How to create .gitignore for various use cases: 96 | Consider you have a project which should be implemented in python, and your chosen IDEs are jupyter notebook and Pycharm. 97 | In this case, ignoring specific files for python won't suffice. In this regard, there is a very useful website [https://www.toptal.com/developers/gitignore](https://www.toptal.com/developers/gitignore) that offers 98 | predefined templates for various IDEs and programing languages. 99 | 100 | ![img_6.png](images/gitignore/img_6.png) 101 | **Image Notes:** 102 | 1) Simply add the programing language and IDEs that you want 103 | 2) click on `Create` to create the `gitignore` file. 104 | 3) Copy/save the output files in a .gitignore file. 105 | 4) Add the file to your project and make sure that you will not commit any specific files to your repository! 106 | 107 | **PS:** Many thanks to [FeryET](https://github.com/FeryET) for introducing this website to me. 108 | 109 | 110 | -------------------------------------------------------------------------------- /removing-renaming-files.md: -------------------------------------------------------------------------------- 1 | # Removing/Renaming Files 2 | 3 | Removing & Renaming files are one of fundamental requirements any Git users would need. 4 | For instance, you might want to correct a typo or merge two files into one file. 5 | There are several use cases for these two functionalities, thereby in this section, we'll cover the following items: 6 | 7 | ## Table of Contents 8 | 1. [How to remove a file?](#how-to-remove-a-file) 9 | 2. [How to remove a file? [Git-Style]](#how-to-remove-a-file-git-style) 10 | 3. [How to rename a file?](#how-to-rename-a-file) 11 | 4. [How to rename a file? [Git-Style]](#how-to-rename-a-file-git-style) 12 | 13 | 14 | ## How to remove a file 15 | 16 | Before removing a file, let's create a file in the previous project which we created, namely [git_01](https://github.com/pooya-mohammadi/git_01/). 17 | 18 | ```commandline 19 | cd git_01 20 | touch hello_world.txt # On Windows, you can create it graphically. 21 | git add hello_world.txt # Add to stage(one step before commiting) 22 | git commit -m "Add hello_world.txt" # commit the changes on stage 23 | git push origin main # push the changes to remote repository 24 | ``` 25 | ![img_2.png](images/remove-rename-files/add_hello_world.png) 26 | 27 | Now, let's remove the file simply by deleting it: 28 | ```commandline 29 | rm hello_world.txt # On Windows, you can remove it graphically. 30 | git status 31 | ``` 32 | 33 | ![img_2.png](images/remove-rename-files/rm_file.png) 34 | 35 | **Image Notes:** 36 | 1. `hello_world.txt` is deleted, but the changes are not staged!! 37 | 2. To restore a removed file use: `git restore `. Using this command, you will have the exact file present on your git project/directory! 38 | 3. For adding the changes cause by removing a file you should use the following command: `git rm ` 39 | 40 | So let's add the changes to stage: 41 | ```commandline 42 | git rm hello_world.txt 43 | git status 44 | ``` 45 | ![img_2.png](images/remove-rename-files/rm_file.png) 46 | 47 | **Image Notes:** 48 | 1. the `rm` command after `git` is one of the git commands, and it works on Windows/Linux/Mac. 49 | 2. the changes now are transfered to stage, ready for being committed 50 | 3. Like always, by using `git restored --staged ` command one can restore the files which are staged! 51 | 52 | Let's commit and push the changes: 53 | ```commandline 54 | git commit -m "Remove hello_world.txt" 55 | git push origin main 56 | ``` 57 | 58 | ![img_2.png](images/remove-rename-files/push_rm.png) 59 | 60 | ## How to remove a file [Git Style] 61 | Git provides a way to remove files directly that you might find more convenient to use. To explore it, let's create a file like the previous step: 62 | ```commandline 63 | cd git_01 64 | touch hello_world.txt # On Windows, you can create it graphically. 65 | git add hello_world.txt # Add to stage(one step before commiting) 66 | git commit -m "Add hello_world.txt" # commit the changes on stage 67 | git push origin main # push the changes to remote repository 68 | ``` 69 | Now, let's remove it using git: 70 | ```commandline 71 | git rm hello_world.txt 72 | git status 73 | ``` 74 | 75 | ![img_2.png](images/remove-rename-files/rm-git-style.png) 76 | 77 | **Image Note:** 78 | 1. As it's shown in the image above, the file is removed directly. It's not present in the project's directory. 79 | 2. The changes are directly added to the `stage` and ready to be committed! 80 | 81 | Let's commit and remove them: 82 | ```commandline 83 | git commit -m "Remove hello_world.txt" 84 | git push origin main 85 | ``` 86 | ![img_2.png](images/remove-rename-files/push-rm-git-style.png) 87 | 88 | **NOTE:** The commit is tagged as `delete mode` 89 | 90 | ## How to rename a file 91 | 92 | Renaming a file is a bit trickier than removing it because we still want to have the file but in another name! 93 | 94 | So as always, let's create a file with a typo in its name. We'll continue our experiments on [git_01](https://github.com/pooya-mohammadi/git_01/) project. 95 | 96 | 97 | ```commandline 98 | cd git_01 99 | touch names_datbase.txt # On Windows, you can create it graphically. 100 | git add names_datbase.txt 101 | git commit -m "names_database.txt" 102 | git push origin main 103 | ``` 104 | ![img_2.png](images/remove-rename-files/rename-add-file.png) 105 | 106 | Now, let's correct the typo by renaming it! 107 | 108 | ```commandline 109 | mv names_datbase.txt names_database.txt # On Windows, you can rename it graphically! 110 | git status 111 | ``` 112 | 113 | ![img_2.png](images/remove-rename-files/rename_file.png) 114 | 115 | **Image Notes:** 116 | 1. As it's evident, renaming a file compasses two steps: 117 | 1. Removing it 118 | 2. Creating a new one 119 | 2. Therefore, the previous name must be removed from git and the new one must be added! 120 | 121 | Let's take the appropriate actions to completing the renaming process: 122 | ```commandline 123 | git rm names_datbase.txt # remove the one with typo 124 | git add names_database.txt # Add the new one 125 | git status 126 | ``` 127 | 128 | ![img_2.png](images/remove-rename-files/rm-add-file.png) 129 | 130 | As depicted in the image above, `git` finds out that a renaming is going on and tags the files as `renamed` 131 | 132 | The changes are applied to `stage` and they are ready to be committed: 133 | ```commandline 134 | git commit -m "[Fix-Typo] Rename names_datbase.txt to names_database.txt" 135 | git push origin main # push the changes to remote repository! 136 | ``` 137 | ![img_2.png](images/remove-rename-files/commit-rename.png) 138 | 139 | **NOTE:** Even in the commit message it mentions the renaming process! 140 | 141 | ## How to rename a file [Git Style] 142 | Git also provides a way to rename files directly that you might find more convenient to use. 143 | To explore it, let's create a file containing a typo like the previous section: 144 | ```commandline 145 | cd git_01 146 | touch names_datbase.txt # On Windows, you can create it graphically. 147 | # There is a typo in the name of the file! 148 | git add names_datbase.txt 149 | git commit -m "names_database.txt" 150 | git push origin main 151 | ``` 152 | 153 | In order to correct the intentionally introduced typo, we can use `git mv`: 154 | ```commandline 155 | git mv names_datbase.txt names_database.txt 156 | git status 157 | ``` 158 | 159 | ![img_2.png](images/remove-rename-files/mv-git-style.png) 160 | 161 | **Image Notes:** 162 | 1. `git mv` is git command can be executed in any operation-systems(os) like Windows and Linux 163 | 2. The renaming process is done automatically 164 | 3. The changes are added to `stage` automatically as well and are ready to be committed! 165 | 166 | ```commandline 167 | git commit -m "[Fix-Typo] Rename names_datbase.txt to names_database.txt" 168 | git push origin main 169 | ``` 170 | 171 | ![img_2.png](images/remove-rename-files/push-mv-git-style.png) 172 | 173 | **NOTE:** the commit is tagged as `rename`! -------------------------------------------------------------------------------- /Readme.md: -------------------------------------------------------------------------------- 1 | # Introduction to Git 2 | ![](images/readme/gitgithub.png)
3 | This repo contains a series of notes for using Git and GitHub.
4 | It's aimed at making it easy to work with Git and GitHub practically
5 | I also released a series of YouTube videos based on the content of this repo. You can find the videos in the following link:
6 | [intro_to_git youtube series](https://youtube.com/playlist?list=PL2g_5adpoaeLfkAnqPH3sYQDYLeFYgr0b) 7 | 8 |
9 | 10 | # Table of Contents 11 | 12 | | Lesson Number | Topic | Learning Objectives | YouTube Videos | 13 | |---------------|------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| 14 | | 01 | [Creating a Git Project](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md) | **Git Introduction-Installation & Creating a Git Project:**

1. [What is Git?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#what-is-git)
2. [What can Git do?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#what-can-git-do)
3. [How to create a project and control its versions using git?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#how-to-create-a-project-and-control-its-versions-using-git)
4. [How to check a project's git history?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#how-to-check-a-projects-git-history)
5. [How to move backward and forward between versions?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#how-to-move-backward-and-forward-between-versions)

|

| 15 | | 02 | [Adding Project to GitHub](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md) | **Adding Project to GitHub:**

1. [How to add our project to a remote server[GitHub]?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#how-to-add-our-project-to-a-remote-servergithub)

|

| 16 | | 03 | [Developing a Project From Different Machines-Rebase](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md) | **Clone, Pull & Solving pull conflicts with Rebase:**

1. [How to clone a project?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/developing_a_project_from_different_machines.md#how-to-clone-a-project)
2. [how to pull changes made from other git repositories?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/developing_a_project_from_different_machines.md#how-to-tackle-errors-and-conflicts-that-may-occur-in-this-way)
3. [how to tackle errors and conflicts that may occur in this way?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/developing_a_project_from_different_machines.md#how-to-tackle-errors-and-conflicts-that-may-occur-in-this-way)

|

| 17 | | 04 | [Developing a Project From Different Machines-Merge](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md) | **Solving pull conflicts with Merge:**

1. [how to tackle errors and conflicts using merge?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/developing_a_project_from_different_machines.md#how-to-tackle-errors-and-conflicts-using-merge)

|

| 18 | | 05 | [Removing and Renaming Files](https://github.com/pooya-mohammadi/intro_to_git/blob/main/removing-renaming-files.md) | **Removing and Renaming Files:**

1. [How to remove a file?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/removing-renaming-files.md#how-to-remove-a-file)
2. [How to remove a file? [Git-Style]](https://github.com/pooya-mohammadi/intro_to_git/blob/main/removing-renaming-files.md#how-to-remove-a-file-git-style)
3. [How to rename a file?](https://github.com/pooya-mohammadi/intro_to_git/blob/main/removing-renaming-files.md#how-to-rename-a-file)
4. [How to rename a file? [Git-Style]](https://github.com/pooya-mohammadi/intro_to_git/blob/main/removing-renaming-files.md#how-to-rename-a-file-git-style)

|

| 19 | | 06 | [.gitignore](https://github.com/pooya-mohammadi/intro_to_git/blob/main/gitignore.md) | **How to ignore files and directories from unintentionally being committed:**

1. [Simulating a use case for gitignore](https://github.com/pooya-mohammadi/intro_to_git/blob/main/gitignore.md#simulating-a-use-case-for-gitignore)
2. [How to add .gitignore at the time of project creation in GitHub](https://github.com/pooya-mohammadi/intro_to_git/blob/main/gitignore.md#how-to-add-gitignore-at-the-time-of-project-creation-in-github)
3. [How to create .gitignore for various use cases](https://github.com/pooya-mohammadi/intro_to_git/blob/main/gitignore.md#how-to-create-gitignore-for-various-use-cases)

|

| 20 | 21 | ## 🌟 Spread the word! 22 | 23 | I would appreciate it if you could support the active development of this repo by: 24 | - Adding a GitHub Star to the project! 25 | - Following my profile [https://github.com/pooya-mohammadi](https://github.com/pooya-mohammadi) on GitHub 26 | - Following my profile [https://youtube.com/PooyaMohammadiKazaj](https://youtube.com/PooyaMohammadiKazaj) on YouTube 27 | 28 | Thanks so much for your interest in growing the reach of the repo! 29 |

(back to top)

30 | 31 | ## ⚠️ License 32 | 33 | Distributed under the MIT License. See `LICENSE` for more information. 34 | 35 |

(back to top)

36 | -------------------------------------------------------------------------------- /creating_git_project.md: -------------------------------------------------------------------------------- 1 | # Creating a Git Project 2 | 3 | Git is a version control system which is mainly used by developers to version codes. In this section, we'll cover the 4 | following items: 5 | 6 | 1. [What is Git?](#what-is-git) 7 | 2. [What can Git do?](#what-can-git-do) 8 | 3. [How to create a project and control its versions using git?](#how-to-create-a-project-and-control-its-versions-using-git) 9 | 4. [How to check a project's git history?](#how-to-check-a-projects-git-history) 10 | 5. [How to move backward and forward between versions?](#how-to-move-backward-and-forward-between-versions) 11 | 6. [How to add our project to a remote server[GitHub]?](#how-to-add-our-project-to-a-remote-servergithub) 12 | 13 |

14 | Introduction to Git: Install Git, Create a git project, Go back and forth between versions 15 |

16 | 17 | ## What is Git? 18 | Git is an open-source version control system initially developed in 2005 by Linus Torvalds. 19 | It's, by far, the most used VCS in the world. 20 | It provides features for developers enabling them to control different versions of their files and codes. 21 | 22 | ## What can Git do? 23 | Git is mainly used because of following reasons 24 | * Go back and forth between versions or changes which are made 25 | * Check change history 26 | * review changes between different versions 27 | * several other features which we'll review in the next chapters. 28 | 29 | ## How to create a project and control its versions using git 30 | To start a Git based project. First, we need to install it:
31 | ### Installation 32 | linux users: 33 | ```commandline 34 | sudo apt-get install git 35 | ``` 36 | Windows users:
37 | Download git from the following link and install it.
38 | [git download link](https://git-scm.com/downloads) 39 |
Use the default options and install it. 40 | 41 | Then, open a terminal/cmd and run the following command to start a project: 42 | 43 | ```commandline 44 | mkdir git_01 # change git_01 to your desired project's name 45 | cd git_01 # change directory 46 | git init # Initialize a new git database 47 | ``` 48 | If everything goes fine, you should be able to see a file named `.git` in your project's directory.
49 | The output should also be like below:
50 | ![img.png](images/create_git_project/img_init.png) 51 | 52 | ### Now, let's create our first file. 53 | 54 | ```commandline 55 | touch Readme.md # If your are on Windows, simply create a text file and change its name and extension to Readme.md 56 | git status # to check the status of your project 57 | ``` 58 | ![img.png](images/create_git_project/img_status.png) 59 | 60 | **Image Notes:** 61 | 1. branch name: main 62 | 1. In a git project, one create multiple branches, we'll get to it. 63 | 2. Your branch name might be master. 64 | 3. run `git branch -M main` to rename your branch to `main` as well. 65 | 2. No commits yet: We'll create a commit soon 66 | 3. untracked files: Readme.md 67 | 1. untracked files are those which are not added to git's staging area. They are not part of git. They are kind of dangling files. 68 | 2. Staging Area: the staging area is where you put your `modified codes/files` before `versioning it` or before taking snapshots from them. 69 | 3. To add a file to staging area use `git add ...` 70 | 4. Note: you don't need to add every file you have to the staging area. Only add those that you want to take snapshot or create a version of it. 71 | 72 | ### So let's add our first file to the staging area. 73 | 74 | ```commandline 75 | git add Readme.md # Add to the staging area 76 | git status # Use this each time you make a change. It's a lifesaver. 77 | ``` 78 | ![img.png](images/create_git_project/img_add.png) 79 | 80 | **Image Notes:** 81 | 1. Changes to be committed: new file: Readme.md 82 | 1. There is only one new file which can be committed. 83 | 2. Commit: Committing a staged file means that you are creating version of it and adding it to the git's database at the same time. 84 | 3. After committing a file, you can access that version anytime you desire(we'll see how to access different versions) 85 | 2. How to remove a file from staging area: `git rm --cached ...` 86 | 1. Note:**By using this command the file will be removed from future versions. It's as if it was not existed ever!** 87 | 88 | ### Let's create our first commit: 89 | Commit structure is as follows: 90 | ```commandline 91 | # git commit -m commit-message 92 | # ex: 93 | git commit -m "Add Readme.md" 94 | git status 95 | ``` 96 | 97 | The output should be like below if you had only `Readme.md` in your project's directory:
98 | ![img.png](images/create_git_project/img_commit.png) 99 | **Image Notes:** 100 | 1. [main f38854a] Add Readme.md: [branch-name commit-hash] commit message 101 | 1. Your commit-hash might differ than mine! 102 | 2. 1 file changed, 0 insertions(+), 0 deletions(-) 103 | 1. We created a file 104 | 2. we didn't delete or insert anything to any file 105 | 106 | 107 | That's it. We have now the first version of our file. 108 | 109 | Note: 110 |
Before your first commit, you will be asked to enter your a commit email.
111 | Enter the email that you are going to create a GitHub account and the username that you want to use for your GitHub. 112 | 113 | ![img_1.png](images/create_git_project/img_commit_email.png) 114 | 115 | You can change them at any time... 116 | 117 | ### Let's make a change and commit it as well as the previous one. 118 | 119 | ```commandline 120 | # open Readme.md using a text editor and add the following line 121 | # # Introduction to Git 122 | # an empty line 123 | git status 124 | ``` 125 | ![img_1.png](images/create_git_project/img_git_modified.png) 126 | ```commandline 127 | git add Readme.md # Before commiting a file, you should add it to stating area. 128 | git status 129 | ``` 130 | ![img.png](images/create_git_project/img_change_commit.png) 131 | 132 | **Image Notes:** 133 | 1. I used nano to modify Readme.md(a linux app for editing text files) 134 | 2. Changes to be committed: It means that you have added some files to staging area, and it's ready to be committed. 135 | 3. If you don't want to include the newly applied changes to your file, you can simply restore it using `git restore --staged ...` 136 | 1. This command removes the changed file from the staging area. **It does not remove the whole file from git cache or future commits as in the previous command** 137 | 138 | ```commandline 139 | git commit -m "Add header Readme.md" # try to add an informative commit message(we'll talk about it in the next notes) 140 | git status # an inseparable part of our commands :) 141 | ``` 142 | 143 | ![img.png](images/create_git_project/img_modify_readme.png) 144 | 145 | **Image Notes:** 146 | 1. I used nano to modify Readme.md(a linux app for editing text files) 147 | 2. [main 22b2390] Add header Readme.md: [branch-name commit-hash] commit message 148 | 1. commit-hash is a unique code used for labeling different versions. 149 | 3. 1 file changed, 2 insertions(+) 150 | 1. We changed one file and inserted two lines to `Readme.md` 151 | 2. First line was the header 152 | 3. The second line was an empty new line. Yours might be `1 insertions(+)` which is ok... 153 | 154 | So far, we have created two versions. Let's step to the next section and check the history. 155 | 156 | ## How to check a project's git history 157 | To check git history of project run the following command: 158 | ```commandline 159 | git log --oneline 160 | ``` 161 | 162 | ![img.png](images/create_git_project/img_git_history.png) 163 | 164 | **Image Notes:** 165 | 1. commit-hash commit-message 166 | 2. All the commits with their hash-codes and their messages are shown 167 | 3. (HEAD -> main) -> this shows the latest version of your project and its branch name. 168 | 169 | ## How to move backward and forward between versions 170 | It does not matter in which direction you want to go. You only should have the hash-code. 171 | 172 | ```commandline 173 | git checkout hash-code 174 | ``` 175 | Let's get back to the first commit: 176 | ```commandline 177 | git checkout f38854a 178 | ``` 179 | Note: your commit-hash may differ, use your own. To fetch all your git's history, check the previous section.
180 | ![img.png](images/create_git_project/img_checkout.png) 181 | 182 | **Image Notes: This time let's start from the end** 183 | 1. The `Readme.md` contains nothing, as if we have not added anything to it. # you can open Readme.md using your favorite text editor. 184 | 2. The history show's only one line because each version/commit has its own history which depicts what's **prior** to it. 185 | 3. HEAD is now at f38854a Add Readme.md -> show's on which commit-hash the git is. 186 | 4. `detached HEAD`: It means that this is not an independent branch like `main`(yours might be `master`). 187 | 1. It's not recommended to make change on `detached HEAD` because it can cause several issues. Its intention is to let you look around and so on. 188 | 2. If you want to make commits on this state and retain them you should create a new branch(we'll talk about it). 189 | 190 | ### How to get back where we were before `checkout` 191 | ```commandline 192 | git checkout main # your branch name(yours might be `master`) 193 | ``` 194 | ![img.png](images/create_git_project/img_checkout_main.png) 195 | 196 | Everything is back to the way we left. It's amazing! 197 | 198 | ## How to add our project to a remote server[GitHub] 199 | 200 | ### Why do we need a remote server 201 | 1. To make sure our projects don't get lost due to computer crashes. Maintain our projects. 202 | 2. We can share it with others. Contribute to open-source community. 203 | 3. We can do teamwork. Collaborate on various projects. 204 | 4. We can get help from others by issues and forks!! 205 | 5. and so on... 206 | ### How to set one 207 | First, create an account on [GitHub.com](https://github.com). Then Log in to your page.
208 | ![img.png](images/create_git_project/github_new.png) 209 | Click on the new button to create a new project.
210 | ![img.png](images/create_git_project/img_create_project_github.png) 211 | 212 | **Image Notes:** 213 | 1. Repository name should be unique comparing to your other projects 214 | 2. You can create a public, which every can see, or a private project, which only you can see it. 215 | 3. You can check Add a README file. I have not checked it because we have already one Readme.md file. 216 | 4. We'll discuss the rest later. 217 | 218 | Click on `Create repository` button. Then you'll see the following image: 219 | ![img.png](images/create_git_project/img_github_repository_info.png) 220 | 221 | **Image Notes:** 222 | 1. or HTTPS/SSH 223 | 1. These two indicate how you establish your connection with the remote server. 224 | 2. By default, it is set to `SSH` 225 | 1. The Secure Shell Protocol (SSH) is a cryptographic network protocol for operating network services securely over an unsecured network.[Wikipedia](https://en.wikipedia.org/wiki/Secure_Shell) 226 | 2. In this part we'll continue with `SSH` 227 | 2. ...create a new repository on the command line: 228 | 1. We checked how to create a `Readme.md` file and how to commit 229 | 2. The last three lines show how to change your branch name to `main`, how to add a remote server to a local git, and how to `push`/send our codes to the remote server 230 | 3. ...or push an existing repository from the command line 231 | 1. What we have done so far lies in this category 232 | 2. The first line is used to add a new remote 233 | 3. The second line renames your branch 234 | 4. the third line pushes/sends the files to remote server 235 | 236 | So let's add the remote server: 237 | ```commandline 238 | git remote add origin git@github.com:pooya-mohammadi/git_01.git 239 | ``` 240 | Note: your remote server's name can be other than `origin`. By convention everyone chooses `origin` as their remote servers name. 241 | 242 | You can rename your branch if it's not `main` 243 | ```commandline 244 | git branch -M main 245 | ``` 246 | 247 | Then, push your commits to the remote server: 248 | ```commandline 249 | git push -u origin main 250 | ``` 251 | You will get a message as below:
252 | ![img.png](images/create_git_project/github-push-error.png) 253 | 254 | **Image notes:** 255 | 1. As it is clear in the image, the server blocks the request because we have not set the publickey. 256 | 2. You can consider than the correct credentials are not set, so the remote server does not authenticate our push request and does not consider it valid. 257 | 258 | **Note:** 259 | 260 | ### Let's assign public key to GitHub 261 | linux users: 262 | ```commandline 263 | sudo apt-get install openssh-server # install 264 | sudo systemctl enable ssh # enable 265 | sudo systemctl start ssh # start 266 | 267 | ssh-keygen # generates a public key. You can specify a name or simply follow the defaults using enter key. 268 | cat ~/.ssh/id_rsa.pub 269 | ``` 270 | Windows users:
271 | Open Powershell and enter the following command: 272 |
[how to install ssh on Windows reference](https://docs.microsoft.com/en-us/windows-server/administration/openssh/openssh_install_firstuse?tabs=powershell) 273 | ```commandline 274 | (New-Object Security.Principal.WindowsPrincipal([Security.Principal.WindowsIdentity]::GetCurrent())).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator) 275 | Get-WindowsCapability -Online | Where-Object Name -like 'OpenSSH*' 276 | ssh-keygen.exe # generates a public key. You can specify a name or simply follow the defaults using enter key. 277 | cat ~\.ssh\id_rsa.pub 278 | ``` 279 | The last line prints out the public key. Copy the key. 280 | ![img.png](images/create_git_project/img_github_ssh.png) 281 | 282 | **Image Note:** 283 | 1. First, click on `settings` 284 | 2. Then, click on `SSH and GPG keys` 285 | 3. On the new page, click on `New SSH key` 286 | 4. Add a Title(it could be anything) 287 | 5. Paste your publickey in the box titled Key 288 | 6. And, Click on Add SSH key 289 | 290 | ![img.png](images/create_git_project/img_github_add_ssh.png) 291 | 292 | Then, run the push command again: 293 | ```commandline 294 | git push -u origin main 295 | ``` 296 | 297 | ![img.png](images/create_git_project/img_push_success.png) 298 | 299 | Finally, refresh the main page of your project you should be able to see that Readme.md is uploaded. 300 | ![img.png](images/create_git_project/img_git_success.png) 301 | 302 | Note: 303 | > The `-u` flag is used to set origin as the upstream remote in your git config. 304 | As you push a branch successfully or up to date it, it adds upstream reference.
305 | As you push local branch with (the)`git push -u` option, that local branch is linked with the remote branch automatically. 306 |
The advantage is, you may use `git pull` without any arguments. 307 | [link to note's reference](https://www.interglobalmedianetwork.com/blog/2020-02-15-the-importance-and-advantage-of-git-push-u) 308 | 309 | We'll get to pull later. 310 | -------------------------------------------------------------------------------- /developing_a_project_from_different_machines.md: -------------------------------------------------------------------------------- 1 | # Developing a project from different machines 2 | 3 | It's a common need that git users may want to access to their projects from different machines/destinations. 4 | For instance, a student may want to work on a project using their laptop and a system in their campus. 5 | Or a developer might have two operating systems, say Linux and Windows, thereby they need a way to sync their 6 | codes and files without enduring severe suffering. In this tutorial we will focus on this issue. 7 | 8 | In this section, we will answer the following questions: 9 | ## Table of Contents 10 | 1. [how to clone a project?](#how-to-clone-a-project) 11 | 2. [how to pull changes made from other git repositories?](#how-to-tackle-errors-and-conflicts-that-may-occur-in-this-way) 12 | 3. [how to tackle errors and conflicts that may occur in this way?](#how-to-tackle-errors-and-conflicts-that-may-occur-in-this-way) 13 | 4. [how to tackle errors and conflicts using merge?](#how-to-tackle-errors-and-conflicts-using-merge) 14 | 15 |

16 | Introduction to Git: Cloning, Pulling, solving merge conflict with rebase 17 |

18 | 19 | ## how to clone a project? 20 | Before beginning this part, consider that you are working on a project and has created a GitHub repository. 21 | To make the process easier, we will have two identical versions of our GitHub repository in two different destinations. 22 | 23 | Now, let's get back to our first project that we created in the [cloning_remote_project section](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md). 24 | To clone a project we have two options as depicted in the following image:
25 | ![img.png](images/developing_a_project_from_different_machines/cloning_options.png)
26 | Options: HTTPS and SSH 27 | 28 | 1. SSH:
29 | If you have [established ssh-connection with GitHub](https://github.com/pooya-mohammadi/intro_to_git/blob/main/creating_git_project.md#lets-assign-public-key-to-github), 30 | you can choose this option. Then simply copy the address appeared at the bar right below the SSH-button. 31 | 32 | 2. HTTPS:
33 | This is used when you don't have ssh-connection and simply want to authenticate each time you are making a change on the project. 34 | Then, copy the address appeared at the bar right below the buttons.
35 | 36 | **Note:** If you want to clone a project which does not belong to you or your team members, and you simply want to check it without making any changes, you can use HTTPS or SSH. 37 | 38 | For the sake of this tutorial, we shall clone the [git_01](https://github.com/pooya-mohammadi/git_01/) project 39 | to a different directory to have two copies of it in two destinations in order to mimic two machines. 40 | This way, each destination will act as a separate machine. 41 | 42 | To clone a project: 43 | ```commandline 44 | git clone 45 | ``` 46 | In this tutorial, we'll clone the git_01 project with the following git-command: 47 | ``` 48 | mkdir second_machine # This may not work on Windows. Instead, create a new folder named second_machine 49 | cd second_machine # change directory to second_machine 50 | git clone git@github.com:pooya-mohammadi/git_01.git # clone the project 51 | ``` 52 | **Note-1:** To follow with this tutorial, you have to use one of your own projects because you don't have proper permissions to make changes on [git_01](https://github.com/pooya-mohammadi/git_01/) repo.
53 | **Note-2:** Since I have established ssh-connection, I use the ssh-url for cloning the repository.
54 | **Note-3:** To become easily distinguished, another directory, named second_machine, is created. 55 | 56 | The output would be like the following:
57 | 58 | ![cloning_output.png](images/developing_a_project_from_different_machines/cloning_output.png) 59 | 60 | ## how to pull changes made from other git repositories? 61 | In this section, first, we will make a change on our newly cloned repo. Then, we will fetch/get/pull the changes 62 | from the [GitHub repository](https://github.com/pooya-mohammadi/git_01/) without making any direct connection to the 63 | local repository hosting the changes. 64 | 65 | Let's create a simple change by adding a new text-file called `names.txt`. Then let's add a few names to it. 66 | The output should be like the following image: 67 | 68 | ![names_txt_file.png](images/developing_a_project_from_different_machines/names_txt_file.png) 69 | 70 | Let's make a commit and send the changes to the remote server(in this case GitHub) 71 | ```commandline 72 | git add names.txt # add the newly created/modified file to stage 73 | git commit -m "Add names.txt file" # commit(get a snapshot) the staged files 74 | git push origin main # push/send the commits to origin destination on the main branch(our GitHub repo) 75 | ``` 76 | The process of commands: 77 | 78 | ![git-commit-push.png](images/developing_a_project_from_different_machines/git-commit-push.png) 79 | 80 | **NOTE:** I strongly encourage you guys to run `git status` command in any part of the process, so that you would get 81 | familiar with different stages of adding a project to git and GitHub repositories. 82 | 83 | The output of GitHub repository should be like below: 84 | 85 | ![img.png](images/developing_a_project_from_different_machines/github_names.png) 86 | 87 | 88 | ### pull changes 89 | So far, we added a txt file to our repo from the `second_machine/git_01` project. Consider these changes are made by 90 | a team member, and now you want to have these changes on your primary project/`git_01` and make your changes and so on. 91 | 92 | Now, let's compare the commit history of the primary project on our local machine(our system-Windows, Linux, Mac, and so on) 93 | with that of the GitHub repository: 94 | 95 | First, local and primary project:
96 | ```commandline 97 | git log --oneline # to show the logs in oneline(easier to distinguish and comprehend) 98 | ``` 99 | ![primary_commit_history.png](images/developing_a_project_from_different_machines/primary_commit_history.png) 100 | 101 | To see commit history of a GitHub project click on the following button:
102 | ![commits-history](images/developing_a_project_from_different_machines/commits-history.png) 103 | 104 | The output should like below: 105 | ![img.png](images/developing_a_project_from_different_machines/commits_on_github.png) 106 | 107 | As it's evident from the two previous images, our main project is two commits behind from the GitHub repository. 108 | 109 | **NOTE-1:** We made the last one an hour ago, and the one prior to that was made during the recording of the [YouTube 110 | video](https://youtu.be/X5EugV4hza0) of the previous tutorial on my Windows machine.
111 | **NOTE-2:** The first two commits are the same. Not only the commit messages, but also the commit hash codes are the same. 112 | 113 | Now, let's pull the changes on our local machine: 114 | ```commandline 115 | git pull origin main 116 | ``` 117 | ![pull-output](images/developing_a_project_from_different_machines/pull_output.png) 118 | 119 | As you can see in the image below, the names are exactly the same: 120 | ![pull_result.png](images/developing_a_project_from_different_machines/pull_result.png) 121 | 122 | Now, we can make another group of changes, push them to GitHub, and pull them from other machine. 123 | 124 | ## how to tackle errors and conflicts that may occur in this way? 125 | 126 | In this section, we'll try to mimic one the most common conflicts that a git user may occur while trying to sync codes from different machines.
127 | It happens when one forgets to `pull` the changes and make a commit on the same file that has been changed on another machine and pushed to GitHub. 128 | 129 | So, to have this conflict, let's add a new name to our `names.txt` file from our main repository and do the process of adding and pushing to GitHub repo.
130 | ![new_name_main_repo.png](images/developing_a_project_from_different_machines/new_name_main_repo.png) 131 | ```commandline 132 | git add names.txt 133 | git commit -m "Add fourth name to names.txt" 134 | git push origin main 135 | ``` 136 | 137 | Now we have the changes on the git_01 repository on GitHub, but we haven't pulled them from second_machine/git_01. 138 | 139 | Let's imagine that you go home from campus and immediately start coding without pulling the latest commits from GitHub repository.
140 | Trust me, it happens a lot. I make this mistake frequently. 141 | 142 | So, let's change the same fourth line in the second_machine to a new name and try to add and push it without pulling the 143 | latest changes:
144 | ![second_machine_changes.png](images/developing_a_project_from_different_machines/second_machine_changes.png) 145 | ```commandline 146 | cd second_machine/git_01 147 | git add names.txt 148 | git commit -m "[second_machine] Add fourth name to names.txt" 149 | git push origin main 150 | ``` 151 | The error message looks like the following:
152 | ![error_message.png](images/developing_a_project_from_different_machines/error_message.png) 153 | 154 | The hints are really helpful, I'll add them here as well. 155 | > To github.com:pooya-mohammadi/git_01.git 156 | ! [rejected] main -> main (fetch first) 157 | error: failed to push some refs to 'github.com:pooya-mohammadi/git_01.git' 158 | hint: Updates were rejected because the remote contains work that you do 159 | hint: not have locally. This is usually caused by another repository pushing 160 | hint: to the same ref. You may want to first integrate the remote changes 161 | hint: (e.g., 'git pull ...') before pushing again. 162 | hint: See the 'Note about fast-forwards' in 'git push --help' for details. 163 | 164 | So, let's pull the changes and see what happens: 165 | 166 | ![pull_reject.png](images/developing_a_project_from_different_machines/pull_reject.png) 167 | 168 | This is where things get really devastating :facepalm: 169 | 170 | Before we move on, let's recap: 171 | 1. We made a change on our main repository 172 | 2. We pushed it to GitHub 173 | 3. We made a change on the same file on the second_machine/git_01 repository without pulling first 174 | 4. We pushed our changes, the git refused. It said that the remove project contains work that ours does not have 175 | 5. We tried to pull the above-mentioned changes, but again the git refused because the local git has works that interferes with the work on GitHub. 176 | 177 | Let's check the messages from Git itself: 178 | ``` 179 | remote: Enumerating objects: 5, done. 180 | remote: Counting objects: 100% (5/5), done. 181 | remote: Compressing objects: 100% (3/3), done. 182 | Unpacking objects: 100% (3/3), 990 bytes | 990.00 KiB/s, done. 183 | remote: Total 3 (delta 0), reused 3 (delta 0), pack-reused 0 184 | From github.com:pooya-mohammadi/git_01 185 | * branch main -> FETCH_HEAD 186 | c5737ab..cbb38e8 main -> origin/main 187 | hint: You have divergent branches and need to specify how to reconcile them. 188 | hint: You can do so by running one of the following commands sometime before 189 | hint: your next pull: 190 | hint: 191 | hint: git config pull.rebase false # merge (the default strategy) 192 | hint: git config pull.rebase true # rebase 193 | hint: git config pull.ff only # fast-forward only 194 | hint: 195 | hint: You can replace "git config" with "git config --global" to set a default 196 | hint: preference for all repositories. You can also pass --rebase, --no-rebase, 197 | hint: or --ff-only on the command line to override the configured default per 198 | hint: invocation. 199 | fatal: Need to specify how to reconcile divergent branches. 200 | ``` 201 | **NOTE:** on Windows you might not see the previous message and realize that the default strategy 202 | which is `merge` or `--no-rebase` is executed. If you want to reverse this behavior you can execute the following command 203 | and follow the rest of the tutorial: 204 | ```commandline 205 | git reset --hard HEAD 206 | ``` 207 | 208 | We have three options: 209 | 210 | First: 211 | ```commandline 212 | git pull origin main --rebase 213 | ``` 214 | In this one, our local changes/commits will be reapplied on top of the remote changes/commits. 215 | 216 | Second: 217 | ```commandline 218 | git pull origin main --merge 219 | ``` 220 | This will merge the remote changes with local ones, which will result in a merge commit. This may result in merge-conflict as well. 221 | We'll check this in future tutorials. 222 | 223 | Third: 224 | ```commandline 225 | git pull origin main --ff-only 226 | ``` 227 | This will apply the remote changes to local one only if they can be fast-forwarded. 228 | **Note:** In our case, this will be aborted. 229 | 230 | So, Let's pull the changes with `rebase` feature. 231 | ```commandline 232 | git pull origin main --rebase 233 | ``` 234 | 235 | ![merge_conflict.png](images/developing_a_project_from_different_machines/merge_conflict.png) 236 | 237 | Another error-message. In this one, git says it's not able to merge the files because we made the same change on the same line of the same file, so 238 | we have to resolve the conflicts manually. 239 | 240 | **Note:** Most of the time, this is not the case and `rebase` would simply move the local commits on top of the remote ones. 241 | 242 | Like always, let execute life-savor commands:
243 | ![img_1.png](images/developing_a_project_from_different_machines/rebase_git_status_git_branch.png) 244 | 245 | So, a lot to explain: 246 | 1. Interactive rebase in progress. It means the git was not able to resolve the conflicts, thereby the rebasing process is not finished yet. 247 | 2. `names.txt`(the source of the conflict) is now modified. A question arises, what modified it? Because at the last step, we added it to stage and created a commit, so it shouldn't be modified!!! 248 | 3. The output of `git log --oneline` is also weird because the previous commit we made with "[second_machine] Add fourth name to names.txt" commit-message is gone. 249 | 4. Finally, a branch is changed to `rebasing main`, which is another indicator that rebasing it not finished. 250 | 251 | So, let's check the `name.txt`:
252 | ![img_1.png](images/developing_a_project_from_different_machines/names_rebase.png) 253 | 254 | This explains a lot: 255 | ```commandline 256 | <<<<<<< HEAD 257 | Hesam Edrisi 258 | ======= 259 | ``` 260 | This previous section means that this part `Hesam Edirsi` is taken from the HEAD which is on `Add forth name to names.txt`. It's part of the remote 261 | repository. 262 | ```commandline 263 | ======= 264 | Mohammad Mahdi 265 | >>>>>>> d476b3b ([second_machine] Add fourth line) 266 | ``` 267 | This one means that is taken from our latest commit with `d476b3b` hash-code and `[second_machine] Add fourth line` commit message.
268 | This image puts everything into perspective. This is the sign of conflict. The git does not know which one should be saved, 269 | so it provides all the options for the user to decide. 270 | 271 | Let's resolve the conflict:
272 | ![img_1.png](images/developing_a_project_from_different_machines/resolved_conflict.png) 273 | 274 | For the sake of this tutorial, I saved the both names, but it's completely arbitrary and a user can resolve it in any way they desire. 275 | 276 | Now, let's add and push the modified file: 277 | ```commandline 278 | git add names.txt 279 | git rebase --continue 280 | ``` 281 | It will ask you to provide a commit message you can accept the same commit message which was given by yourself in the previous section 282 | or provide another one. In this example, I simply accepted the one we previously provided. 283 | 284 | **NOTE:** Based on the default config of git, a `Vim` editor is opened for editing the commit message after executing `git rebase --continue`. 285 | Following guide would help you while working `Vim`: 286 | 1. To start making a change enter button `i` in your keyboard. It stands for `insert`. 287 | 2. After you made your changes, enter button `Esc` on your keyboard. It exists the previous mode, which in our case is `i` or `insert` 288 | 3. To save and quit, insert the following buttons `:wq`. `w` stands for `write` and `q` stands for `quit`. 289 | 290 | Let's continue with the rest of the process: 291 | ```commandline 292 | gir branch 293 | git log --oneline 294 | git push origin main 295 | ``` 296 | ![img_2.png](images/developing_a_project_from_different_machines/continue_rebase_push.png) 297 | 298 | Now, everything is back to normal. 299 | 1. The conflicts are resolved 300 | 2. The rebase process is successfully continued and finished 301 | 3. branch is on `main` 302 | 4. the commits are in order(the remote commits always come first!) 303 | 5. the push works with no errors! 304 | 305 | Let's see the output:
306 | ![](images/developing_a_project_from_different_machines/github_after_conflicts.png) 307 | 308 | As it's shown in the image the names are pushed to GitHub repo and the latest commit is like the one 309 | on git-history shown in the previous image. 310 | 311 | Final remarks for rebase: 312 | 1. This was one of the most common and also the most complex errors you may encounter while working on a project from different machines. 313 | 2. Most of the time, `rebase` automatically works when the changes are not made on the same file, and you wouldn't need to resolve conflicts manually, but in case if you have to, you know how to resolve it. 314 | 3. In real projects, you may have to resolve more than one file. The process is the same. You have to resolve all the conflicts on all the files. 315 | 316 | ## how to tackle errors and conflicts using merge? 317 | 318 |

319 | Introduction to Git: Solving merge conflicts using merge 320 |

321 | 322 | In this section, we shall check the same conflict and solve it using the `merge`, `--no-rebase`, or the default option. 323 | 324 | To save time, I will create two changes on the `names.txt` file like the previous example. Then, I will push the changes from 325 | `second_machine/git_01` and will make another change on the same file and on the same line from `git_01` project. 326 | 327 | Commit messages: 328 | 1. [second_machine/git_01] Add Nariman Valizadeh # this is pushed to remote server 329 | 2. [git_01] Add Mohammad Rozban # This is not pushed to remote server 330 | 331 | From `git_01` will get the following reject message: 332 | 333 | ![img_2.png](images/developing_a_project_from_different_machines/merge_reject_message.png) 334 | 335 | So, we need to get the changes from remote server. In this section, we'll use `merge` option. 336 | ```commandline 337 | git pull origin main --no-rebase 338 | ``` 339 | 340 | ![img_2.png](images/developing_a_project_from_different_machines/merge_pull.png) 341 | 342 | **Image Notes:** 343 | 1. As it's evident, there is a merge conflict 344 | 2. git status says that `names.txt` is modified 345 | 3. no new branches are created like the one with `rebase` 346 | 4. Important: the commits from remote server is not included in the git log/history! 347 | 348 | Let's resolve the conflicts. The `names.txt` should be like below: 349 | 350 | ![img_2.png](images/developing_a_project_from_different_machines/merge_names_conflict.png) 351 | 352 | As you can see, the Head is `Mohammad Rozban` because it's the last commit we made in this repo. 353 | The `Nariman Valizadeh` is from another commit which in this case only the commit-hash is shown not the commit-message. 354 | 355 | Let's resolve the conflicts like the following: 356 | 357 | ![img_2.png](images/developing_a_project_from_different_machines/merge_resolved_conflicts.png) 358 | 359 | Now, let's add the resolved files and push them: 360 | ```commandline 361 | git add names.txt 362 | git commit -m "[git_01] Resolve merge-conflict | Keep both names" 363 | git push origin main 364 | ``` 365 | 366 | ![img_2.png](images/developing_a_project_from_different_machines/merge_final_push.png) 367 | 368 | **Image Notes & Final remarks for `merge`:** 369 | 1. It has the features of `rebase`. The commits from remote server are located before our local commits 370 | 2. It's easier to understand and work around 371 | 3. It has one extra commit after resolving the conflicts which some may not like it 372 | 4. The output is the same as `rebase`'s output. 373 | 374 | --------------------------------------------------------------------------------