wayfarer 0.4.7 → 0.4.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (773) hide show
  1. checksums.yaml +4 -4
  2. data/.env +17 -0
  3. data/.github/workflows/lint.yaml +8 -6
  4. data/.github/workflows/release.yaml +2 -3
  5. data/.github/workflows/tests.yaml +5 -14
  6. data/.gitignore +2 -2
  7. data/.rubocop.yml +31 -0
  8. data/.vale.ini +6 -3
  9. data/Dockerfile +3 -2
  10. data/Gemfile +21 -0
  11. data/Gemfile.lock +233 -128
  12. data/Rakefile +7 -0
  13. data/docker-compose.yml +13 -14
  14. data/docs/guides/callbacks.md +3 -1
  15. data/docs/guides/configuration.md +10 -35
  16. data/docs/guides/development.md +67 -0
  17. data/docs/guides/handlers.md +7 -7
  18. data/docs/guides/jobs.md +54 -11
  19. data/docs/guides/networking/custom_adapters.md +109 -81
  20. data/docs/guides/networking/http.md +1 -1
  21. data/docs/guides/pages.md +24 -22
  22. data/docs/guides/routing.md +116 -34
  23. data/docs/guides/tasks.md +30 -10
  24. data/docs/guides/tutorial.md +23 -17
  25. data/docs/guides/user_agents.md +11 -9
  26. data/lib/wayfarer/base.rb +9 -8
  27. data/lib/wayfarer/batch_completion.rb +18 -14
  28. data/lib/wayfarer/callbacks.rb +14 -14
  29. data/lib/wayfarer/cli/route_printer.rb +78 -96
  30. data/lib/wayfarer/cli.rb +12 -30
  31. data/lib/wayfarer/gc.rb +6 -1
  32. data/lib/wayfarer/kv.rb +28 -0
  33. data/lib/wayfarer/middleware/base.rb +0 -4
  34. data/lib/wayfarer/middleware/chain.rb +7 -1
  35. data/lib/wayfarer/middleware/content_type.rb +20 -15
  36. data/lib/wayfarer/middleware/controller.rb +1 -1
  37. data/lib/wayfarer/middleware/dedup.rb +9 -3
  38. data/lib/wayfarer/middleware/dispatch.rb +7 -2
  39. data/lib/wayfarer/middleware/normalize.rb +4 -12
  40. data/lib/wayfarer/middleware/router.rb +1 -1
  41. data/lib/wayfarer/middleware/uri_parser.rb +4 -3
  42. data/lib/wayfarer/networking/context.rb +13 -2
  43. data/lib/wayfarer/networking/ferrum.rb +2 -5
  44. data/lib/wayfarer/networking/follow.rb +2 -1
  45. data/lib/wayfarer/networking/pool.rb +11 -12
  46. data/lib/wayfarer/networking/selenium.rb +15 -7
  47. data/lib/wayfarer/networking/strategy.rb +6 -2
  48. data/lib/wayfarer/page.rb +0 -2
  49. data/lib/wayfarer/parsing/xml.rb +1 -1
  50. data/lib/wayfarer/parsing.rb +2 -5
  51. data/lib/wayfarer/redis/barrier.rb +15 -2
  52. data/lib/wayfarer/redis/counter.rb +1 -2
  53. data/lib/wayfarer/routing/dsl.rb +166 -31
  54. data/lib/wayfarer/routing/hash_stack.rb +33 -0
  55. data/lib/wayfarer/routing/matchers/custom.rb +8 -5
  56. data/lib/wayfarer/routing/matchers/{suffix.rb → empty_params.rb} +2 -6
  57. data/lib/wayfarer/routing/matchers/host.rb +15 -9
  58. data/lib/wayfarer/routing/matchers/path.rb +11 -33
  59. data/lib/wayfarer/routing/matchers/query.rb +41 -17
  60. data/lib/wayfarer/routing/matchers/result.rb +12 -0
  61. data/lib/wayfarer/routing/matchers/scheme.rb +13 -5
  62. data/lib/wayfarer/routing/matchers/url.rb +13 -5
  63. data/lib/wayfarer/routing/path_consumer.rb +130 -0
  64. data/lib/wayfarer/routing/path_finder.rb +151 -23
  65. data/lib/wayfarer/routing/result.rb +1 -1
  66. data/lib/wayfarer/routing/root_route.rb +14 -2
  67. data/lib/wayfarer/routing/route.rb +71 -14
  68. data/lib/wayfarer/routing/serializable.rb +28 -0
  69. data/lib/wayfarer/routing/sub_route.rb +53 -0
  70. data/lib/wayfarer/routing/target_route.rb +17 -1
  71. data/lib/wayfarer/stringify.rb +1 -2
  72. data/lib/wayfarer/task.rb +3 -5
  73. data/lib/wayfarer/uri/normalization.rb +120 -0
  74. data/lib/wayfarer.rb +55 -10
  75. data/mise.toml +2 -0
  76. data/mkdocs.yml +8 -17
  77. data/rake/lint.rake +0 -96
  78. data/rake/release.rake +1 -13
  79. data/rake/tests.rake +8 -4
  80. data/requirements.txt +1 -1
  81. data/spec/factories/job.rb +8 -0
  82. data/spec/factories/middleware.rb +2 -2
  83. data/spec/factories/path_finder.rb +11 -0
  84. data/spec/factories/redis.rb +19 -0
  85. data/spec/factories/task.rb +39 -1
  86. data/spec/spec_helpers.rb +50 -57
  87. data/spec/support/active_job_helpers.rb +8 -0
  88. data/spec/support/integration_helpers.rb +21 -0
  89. data/spec/support/redis_helpers.rb +9 -0
  90. data/spec/support/test_app.rb +64 -43
  91. data/spec/{base_spec.rb → wayfarer/base_spec.rb} +32 -36
  92. data/spec/wayfarer/batch_completion_spec.rb +142 -0
  93. data/spec/wayfarer/cli/job_spec.rb +88 -0
  94. data/spec/wayfarer/cli/routing_spec.rb +322 -0
  95. data/spec/{cli → wayfarer/cli}/version_spec.rb +1 -1
  96. data/spec/wayfarer/gc_spec.rb +29 -0
  97. data/spec/{handler_spec.rb → wayfarer/handler_spec.rb} +1 -3
  98. data/spec/{integration → wayfarer/integration}/callbacks_spec.rb +9 -6
  99. data/spec/wayfarer/integration/content_type_spec.rb +37 -0
  100. data/spec/wayfarer/integration/custom_routing_spec.rb +51 -0
  101. data/spec/{integration → wayfarer/integration}/gc_spec.rb +9 -13
  102. data/spec/{integration → wayfarer/integration}/handler_spec.rb +9 -10
  103. data/spec/{integration → wayfarer/integration}/page_spec.rb +16 -14
  104. data/spec/{integration → wayfarer/integration}/params_spec.rb +4 -4
  105. data/spec/{integration → wayfarer/integration}/parsing_spec.rb +7 -32
  106. data/spec/wayfarer/integration/retry_spec.rb +112 -0
  107. data/spec/{integration → wayfarer/integration}/stage_spec.rb +6 -6
  108. data/spec/{middleware → wayfarer/middleware}/batch_completion_spec.rb +4 -5
  109. data/spec/{middleware → wayfarer/middleware}/chain_spec.rb +20 -15
  110. data/spec/{middleware → wayfarer/middleware}/content_type_spec.rb +18 -21
  111. data/spec/{middleware → wayfarer/middleware}/controller_spec.rb +25 -24
  112. data/spec/wayfarer/middleware/dedup_spec.rb +66 -0
  113. data/spec/wayfarer/middleware/normalize_spec.rb +32 -0
  114. data/spec/{middleware → wayfarer/middleware}/router_spec.rb +18 -20
  115. data/spec/{middleware → wayfarer/middleware}/stage_spec.rb +11 -10
  116. data/spec/wayfarer/middleware/uri_parser_spec.rb +63 -0
  117. data/spec/{middleware → wayfarer/middleware}/user_agent_spec.rb +34 -32
  118. data/spec/wayfarer/networking/capybara_spec.rb +13 -0
  119. data/spec/{networking → wayfarer/networking}/context_spec.rb +47 -38
  120. data/spec/wayfarer/networking/ferrum_spec.rb +13 -0
  121. data/spec/{networking → wayfarer/networking}/follow_spec.rb +9 -4
  122. data/spec/wayfarer/networking/http_spec.rb +12 -0
  123. data/spec/{networking → wayfarer/networking}/pool_spec.rb +11 -9
  124. data/spec/wayfarer/networking/selenium_spec.rb +12 -0
  125. data/spec/{networking → wayfarer/networking}/strategy.rb +35 -56
  126. data/spec/{page_spec.rb → wayfarer/page_spec.rb} +3 -3
  127. data/spec/{parsing → wayfarer/parsing}/json_spec.rb +1 -1
  128. data/spec/{parsing/xml_spec.rb → wayfarer/parsing/xml_parse_spec.rb} +4 -3
  129. data/spec/{redis → wayfarer/redis}/barrier_spec.rb +5 -4
  130. data/spec/wayfarer/redis/counter_spec.rb +34 -0
  131. data/spec/{redis → wayfarer/redis}/pool_spec.rb +3 -2
  132. data/spec/{routing → wayfarer/routing}/dsl_spec.rb +12 -22
  133. data/spec/wayfarer/routing/hash_stack_spec.rb +63 -0
  134. data/spec/wayfarer/routing/integration_spec.rb +101 -0
  135. data/spec/wayfarer/routing/matchers/custom_spec.rb +39 -0
  136. data/spec/wayfarer/routing/matchers/host_spec.rb +56 -0
  137. data/spec/wayfarer/routing/matchers/matcher.rb +17 -0
  138. data/spec/wayfarer/routing/matchers/path_spec.rb +43 -0
  139. data/spec/wayfarer/routing/matchers/query_spec.rb +123 -0
  140. data/spec/wayfarer/routing/matchers/scheme_spec.rb +45 -0
  141. data/spec/wayfarer/routing/matchers/url_spec.rb +33 -0
  142. data/spec/wayfarer/routing/path_consumer_spec.rb +123 -0
  143. data/spec/wayfarer/routing/path_finder_spec.rb +409 -0
  144. data/spec/wayfarer/routing/root_route_spec.rb +51 -0
  145. data/spec/wayfarer/routing/route_spec.rb +74 -0
  146. data/spec/wayfarer/routing/sub_route_spec.rb +103 -0
  147. data/spec/wayfarer/uri/normalization_spec.rb +98 -0
  148. data/spec/wayfarer_spec.rb +2 -2
  149. data/wayfarer.gemspec +17 -28
  150. metadata +183 -832
  151. data/.rbenv-gemsets +0 -1
  152. data/.ruby-version +0 -1
  153. data/RELEASING.md +0 -17
  154. data/docs/cookbook/user_agent.md +0 -7
  155. data/docs/design.md +0 -36
  156. data/docs/guides/jobs/error_handling.md +0 -40
  157. data/docs/reference/configuration.md +0 -36
  158. data/lib/wayfarer/middleware/lazy.rb +0 -11
  159. data/spec/batch_completion_spec.rb +0 -104
  160. data/spec/cli/job_spec.rb +0 -74
  161. data/spec/cli/routing_spec.rb +0 -101
  162. data/spec/fixtures/dummy_job.rb +0 -9
  163. data/spec/gc_spec.rb +0 -17
  164. data/spec/integration/content_type_spec.rb +0 -145
  165. data/spec/integration/routing_spec.rb +0 -18
  166. data/spec/middleware/dedup_spec.rb +0 -71
  167. data/spec/middleware/dispatch_spec.rb +0 -59
  168. data/spec/middleware/normalize_spec.rb +0 -60
  169. data/spec/middleware/uri_parser_spec.rb +0 -53
  170. data/spec/networking/capybara_spec.rb +0 -12
  171. data/spec/networking/ferrum_spec.rb +0 -12
  172. data/spec/networking/http_spec.rb +0 -12
  173. data/spec/networking/selenium_spec.rb +0 -12
  174. data/spec/redis/counter_spec.rb +0 -44
  175. data/spec/routing/integration_spec.rb +0 -110
  176. data/spec/routing/matchers/custom_spec.rb +0 -31
  177. data/spec/routing/matchers/host_spec.rb +0 -49
  178. data/spec/routing/matchers/path_spec.rb +0 -43
  179. data/spec/routing/matchers/query_spec.rb +0 -137
  180. data/spec/routing/matchers/scheme_spec.rb +0 -25
  181. data/spec/routing/matchers/suffix_spec.rb +0 -41
  182. data/spec/routing/matchers/uri_spec.rb +0 -27
  183. data/spec/routing/path_finder_spec.rb +0 -33
  184. data/spec/routing/root_route_spec.rb +0 -29
  185. data/spec/routing/route_spec.rb +0 -43
  186. data/spec/support/static/git-scm.com/assets/application-38b0d42ff05ffea45841edebbd14b75b89585646153808e82907c2c5c11f324b.js +0 -772
  187. data/spec/support/static/git-scm.com/assets/application-cafcf280f67db0e6d8168ba98a38da878769a9d5f37793b68ffb963a02d185e0.css +0 -1
  188. data/spec/support/static/git-scm.com/assets/modernize-b3ebe0c31c24f230dc62179d3e1030d2e57a53b1668d9382c0a27dbd44a94beb.js +0 -20
  189. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-Bash.html +0 -751
  190. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-PowerShell.html +0 -804
  191. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-Sublime-Text.html +0 -728
  192. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-Visual-Studio-Code.html +0 -751
  193. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-Visual-Studio.html +0 -740
  194. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Git-in-Zsh.html +0 -765
  195. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Graphical-Interfaces.html +0 -931
  196. data/spec/support/static/git-scm.com/book/en/v2/Appendix-A:-Git-in-Other-Environments-Summary.html +0 -702
  197. data/spec/support/static/git-scm.com/book/en/v2/Appendix-B:-Embedding-Git-in-your-Applications-Command-line-Git.html +0 -720
  198. data/spec/support/static/git-scm.com/book/en/v2/Appendix-B:-Embedding-Git-in-your-Applications-Dulwich.html +0 -746
  199. data/spec/support/static/git-scm.com/book/en/v2/Appendix-B:-Embedding-Git-in-your-Applications-JGit.html +0 -889
  200. data/spec/support/static/git-scm.com/book/en/v2/Appendix-B:-Embedding-Git-in-your-Applications-Libgit2.html +0 -1003
  201. data/spec/support/static/git-scm.com/book/en/v2/Appendix-B:-Embedding-Git-in-your-Applications-go-git.html +0 -792
  202. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Administration.html +0 -745
  203. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Basic-Snapshotting.html +0 -840
  204. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Branching-and-Merging.html +0 -829
  205. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Debugging.html +0 -731
  206. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Email.html +0 -766
  207. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-External-Systems.html +0 -721
  208. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Getting-and-Creating-Projects.html +0 -746
  209. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Inspection-and-Comparison.html +0 -735
  210. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Patching.html +0 -742
  211. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Plumbing-Commands.html +0 -715
  212. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Setup-and-Config.html +0 -863
  213. data/spec/support/static/git-scm.com/book/en/v2/Appendix-C:-Git-Commands-Sharing-and-Updating-Projects.html +0 -802
  214. data/spec/support/static/git-scm.com/book/en/v2/Customizing-Git-An-Example-Git-Enforced-Policy.html +0 -1200
  215. data/spec/support/static/git-scm.com/book/en/v2/Customizing-Git-Git-Attributes.html +0 -1134
  216. data/spec/support/static/git-scm.com/book/en/v2/Customizing-Git-Git-Configuration.html +0 -1315
  217. data/spec/support/static/git-scm.com/book/en/v2/Customizing-Git-Git-Hooks.html +0 -876
  218. data/spec/support/static/git-scm.com/book/en/v2/Customizing-Git-Summary.html +0 -704
  219. data/spec/support/static/git-scm.com/book/en/v2/Distributed-Git-Contributing-to-a-Project.html +0 -1667
  220. data/spec/support/static/git-scm.com/book/en/v2/Distributed-Git-Distributed-Workflows.html +0 -859
  221. data/spec/support/static/git-scm.com/book/en/v2/Distributed-Git-Maintaining-a-Project.html +0 -1354
  222. data/spec/support/static/git-scm.com/book/en/v2/Distributed-Git-Summary.html +0 -704
  223. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-A-Short-History-of-Git.html +0 -735
  224. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-About-Version-Control.html +0 -783
  225. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-First-Time-Git-Setup.html +0 -889
  226. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-Getting-Help.html +0 -750
  227. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-Installing-Git.html +0 -879
  228. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-Summary.html +0 -704
  229. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-The-Command-Line.html +0 -711
  230. data/spec/support/static/git-scm.com/book/en/v2/Getting-Started-What-is-Git?.html +0 -857
  231. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Getting-a-Git-Repository.html +0 -816
  232. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Git-Aliases.html +0 -775
  233. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Recording-Changes-to-the-Repository.html +0 -1432
  234. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Summary.html +0 -703
  235. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Tagging.html +0 -1049
  236. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Undoing-Things.html +0 -998
  237. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Viewing-the-Commit-History.html +0 -1172
  238. data/spec/support/static/git-scm.com/book/en/v2/Git-Basics-Working-with-Remotes.html +0 -983
  239. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Basic-Branching-and-Merging.html +0 -1102
  240. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Branch-Management.html +0 -946
  241. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Branches-in-a-Nutshell.html +0 -1020
  242. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Branching-Workflows.html +0 -786
  243. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Rebasing.html +0 -1028
  244. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Remote-Branches.html +0 -1009
  245. data/spec/support/static/git-scm.com/book/en/v2/Git-Branching-Summary.html +0 -705
  246. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Environment-Variables.html +0 -1009
  247. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Git-Objects.html +0 -1209
  248. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Git-References.html +0 -939
  249. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Maintenance-and-Data-Recovery.html +0 -1086
  250. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Packfiles.html +0 -876
  251. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Plumbing-and-Porcelain.html +0 -745
  252. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Summary.html +0 -708
  253. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-The-Refspec.html +0 -872
  254. data/spec/support/static/git-scm.com/book/en/v2/Git-Internals-Transfer-Protocols.html +0 -1043
  255. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Advanced-Merging.html +0 -1605
  256. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Bundling.html +0 -888
  257. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Credential-Storage.html +0 -1035
  258. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Debugging-with-Git.html +0 -861
  259. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Interactive-Staging.html +0 -920
  260. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Replace.html +0 -949
  261. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Rerere.html +0 -983
  262. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Reset-Demystified.html +0 -1236
  263. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Revision-Selection.html +0 -1178
  264. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Rewriting-History.html +0 -1182
  265. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Searching.html +0 -875
  266. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Signing-Your-Work.html +0 -922
  267. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Stashing-and-Cleaning.html +0 -1039
  268. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Submodules.html +0 -1864
  269. data/spec/support/static/git-scm.com/book/en/v2/Git-Tools-Summary.html +0 -705
  270. data/spec/support/static/git-scm.com/book/en/v2/Git-and-Other-Systems-Git-as-a-Client.html +0 -2656
  271. data/spec/support/static/git-scm.com/book/en/v2/Git-and-Other-Systems-Migrating-to-Git.html +0 -1741
  272. data/spec/support/static/git-scm.com/book/en/v2/Git-and-Other-Systems-Summary.html +0 -703
  273. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Generating-Your-SSH-Public-Key.html +0 -759
  274. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Getting-Git-on-a-Server.html +0 -827
  275. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Git-Daemon.html +0 -775
  276. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-GitLab.html +0 -872
  277. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-GitWeb.html +0 -776
  278. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Setting-Up-the-Server.html +0 -870
  279. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Smart-HTTP.html +0 -789
  280. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Summary.html +0 -709
  281. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-The-Protocols.html +0 -963
  282. data/spec/support/static/git-scm.com/book/en/v2/Git-on-the-Server-Third-Party-Hosted-Options.html +0 -711
  283. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Account-Setup-and-Configuration.html +0 -858
  284. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Contributing-to-a-Project.html +0 -1502
  285. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Maintaining-a-Project.html +0 -1218
  286. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Managing-an-organization.html +0 -797
  287. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Scripting-GitHub.html +0 -1059
  288. data/spec/support/static/git-scm.com/book/en/v2/GitHub-Summary.html +0 -704
  289. data/spec/support/static/git-scm.com/book/en/v2/ch00/_abort_merge.html +0 -1605
  290. data/spec/support/static/git-scm.com/book/en/v2/ch00/_add_email_addresses.html +0 -858
  291. data/spec/support/static/git-scm.com/book/en/v2/ch00/_advanced_merging.html +0 -1605
  292. data/spec/support/static/git-scm.com/book/en/v2/ch00/_an_example_git_enforced_policy.html +0 -1200
  293. data/spec/support/static/git-scm.com/book/en/v2/ch00/_annotated_tags.html +0 -1049
  294. data/spec/support/static/git-scm.com/book/en/v2/ch00/_api_comment.html +0 -1059
  295. data/spec/support/static/git-scm.com/book/en/v2/ch00/_bare_repo.html +0 -827
  296. data/spec/support/static/git-scm.com/book/en/v2/ch00/_basic_branching.html +0 -1102
  297. data/spec/support/static/git-scm.com/book/en/v2/ch00/_basic_merge_conflicts.html +0 -1102
  298. data/spec/support/static/git-scm.com/book/en/v2/ch00/_basic_merging.html +0 -1102
  299. data/spec/support/static/git-scm.com/book/en/v2/ch00/_binary_search.html +0 -861
  300. data/spec/support/static/git-scm.com/book/en/v2/ch00/_branch_management.html +0 -946
  301. data/spec/support/static/git-scm.com/book/en/v2/ch00/_branch_references.html +0 -1178
  302. data/spec/support/static/git-scm.com/book/en/v2/ch00/_build_number.html +0 -1354
  303. data/spec/support/static/git-scm.com/book/en/v2/ch00/_bundling.html +0 -888
  304. data/spec/support/static/git-scm.com/book/en/v2/ch00/_changing_multiple.html +0 -1182
  305. data/spec/support/static/git-scm.com/book/en/v2/ch00/_checking_out_conflicts.html +0 -1605
  306. data/spec/support/static/git-scm.com/book/en/v2/ch00/_checking_out_remotes.html +0 -1354
  307. data/spec/support/static/git-scm.com/book/en/v2/ch00/_checking_status.html +0 -1432
  308. data/spec/support/static/git-scm.com/book/en/v2/ch00/_cloning_submodules.html +0 -1864
  309. data/spec/support/static/git-scm.com/book/en/v2/ch00/_commit_guidelines.html +0 -1667
  310. data/spec/support/static/git-scm.com/book/en/v2/ch00/_commit_ranges.html +0 -1178
  311. data/spec/support/static/git-scm.com/book/en/v2/ch00/_commit_status.html +0 -1059
  312. data/spec/support/static/git-scm.com/book/en/v2/ch00/_committing_changes.html +0 -1432
  313. data/spec/support/static/git-scm.com/book/en/v2/ch00/_contrib_file.html +0 -1218
  314. data/spec/support/static/git-scm.com/book/en/v2/ch00/_contributing_project.html +0 -1667
  315. data/spec/support/static/git-scm.com/book/en/v2/ch00/_create_new_branch.html +0 -1020
  316. data/spec/support/static/git-scm.com/book/en/v2/ch00/_credential_caching.html +0 -1035
  317. data/spec/support/static/git-scm.com/book/en/v2/ch00/_custom_importer.html +0 -1741
  318. data/spec/support/static/git-scm.com/book/en/v2/ch00/_data_recovery.html +0 -1086
  319. data/spec/support/static/git-scm.com/book/en/v2/ch00/_delete_branches.html +0 -1009
  320. data/spec/support/static/git-scm.com/book/en/v2/ch00/_editor.html +0 -889
  321. data/spec/support/static/git-scm.com/book/en/v2/ch00/_eg_task_lists.html +0 -1502
  322. data/spec/support/static/git-scm.com/book/en/v2/ch00/_email_hooks.html +0 -876
  323. data/spec/support/static/git-scm.com/book/en/v2/ch00/_email_notification.html +0 -1502
  324. data/spec/support/static/git-scm.com/book/en/v2/ch00/_email_notifications.html +0 -1218
  325. data/spec/support/static/git-scm.com/book/en/v2/ch00/_email_pr.html +0 -1218
  326. data/spec/support/static/git-scm.com/book/en/v2/ch00/_enforcing_commit_message_format.html +0 -1200
  327. data/spec/support/static/git-scm.com/book/en/v2/ch00/_example_markdown.html +0 -1502
  328. data/spec/support/static/git-scm.com/book/en/v2/ch00/_external_merge_tools.html +0 -1315
  329. data/spec/support/static/git-scm.com/book/en/v2/ch00/_fetch_and_push_on_different_repositories.html +0 -1502
  330. data/spec/support/static/git-scm.com/book/en/v2/ch00/_fetching_and_pulling.html +0 -983
  331. data/spec/support/static/git-scm.com/book/en/v2/ch00/_file_annotation.html +0 -861
  332. data/spec/support/static/git-scm.com/book/en/v2/ch00/_first_time.html +0 -889
  333. data/spec/support/static/git-scm.com/book/en/v2/ch00/_generate_ssh_key.html +0 -759
  334. data/spec/support/static/git-scm.com/book/en/v2/ch00/_getting_a_repo.html +0 -816
  335. data/spec/support/static/git-scm.com/book/en/v2/ch00/_getting_git_on_a_server.html +0 -827
  336. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_aliases.html +0 -775
  337. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_am.html +0 -1354
  338. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_amend.html +0 -1182
  339. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_branches_overview.html +0 -1020
  340. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_clean.html +0 -1039
  341. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_cloning.html +0 -816
  342. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_commit_objects.html +0 -1209
  343. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_config.html +0 -1315
  344. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_diff_staged.html +0 -1432
  345. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_gc.html +0 -1086
  346. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_grep.html +0 -875
  347. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_help.html +0 -750
  348. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_hooks.html +0 -876
  349. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_mv.html +0 -1432
  350. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_p4.html +0 -1741
  351. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_p4_branches.html +0 -2656
  352. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_reflog.html +0 -1178
  353. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_refs.html +0 -939
  354. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_reset.html +0 -1236
  355. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_stashing.html +0 -1039
  356. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_submodules.html +0 -1864
  357. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_svn.html +0 -2656
  358. data/spec/support/static/git-scm.com/book/en/v2/ch00/_git_tagging.html +0 -1049
  359. data/spec/support/static/git-scm.com/book/en/v2/ch00/_gitlab_groups_section.html +0 -872
  360. data/spec/support/static/git-scm.com/book/en/v2/ch00/_ignoring.html +0 -1432
  361. data/spec/support/static/git-scm.com/book/en/v2/ch00/_inspecting_remote.html +0 -983
  362. data/spec/support/static/git-scm.com/book/en/v2/ch00/_integration_manager.html +0 -859
  363. data/spec/support/static/git-scm.com/book/en/v2/ch00/_interactive_staging.html +0 -920
  364. data/spec/support/static/git-scm.com/book/en/v2/ch00/_keyword_expansion.html +0 -1134
  365. data/spec/support/static/git-scm.com/book/en/v2/ch00/_libgit2_bindings.html +0 -1003
  366. data/spec/support/static/git-scm.com/book/en/v2/ch00/_manual_remerge.html +0 -1605
  367. data/spec/support/static/git-scm.com/book/en/v2/ch00/_md_code.html +0 -1502
  368. data/spec/support/static/git-scm.com/book/en/v2/ch00/_md_drag.html +0 -1502
  369. data/spec/support/static/git-scm.com/book/en/v2/ch00/_md_emoji.html +0 -1502
  370. data/spec/support/static/git-scm.com/book/en/v2/ch00/_md_quote.html +0 -1502
  371. data/spec/support/static/git-scm.com/book/en/v2/ch00/_merge_button.html +0 -1218
  372. data/spec/support/static/git-scm.com/book/en/v2/ch00/_merge_log.html +0 -1605
  373. data/spec/support/static/git-scm.com/book/en/v2/ch00/_merge_rebase_work.html +0 -1028
  374. data/spec/support/static/git-scm.com/book/en/v2/ch00/_new_repo_dropdown.html +0 -1218
  375. data/spec/support/static/git-scm.com/book/en/v2/ch00/_not_center.html +0 -1218
  376. data/spec/support/static/git-scm.com/book/en/v2/ch00/_org_page.html +0 -797
  377. data/spec/support/static/git-scm.com/book/en/v2/ch00/_other_client_hooks.html +0 -876
  378. data/spec/support/static/git-scm.com/book/en/v2/ch00/_p4_git_fusion.html +0 -2656
  379. data/spec/support/static/git-scm.com/book/en/v2/ch00/_patches_from_email.html +0 -1354
  380. data/spec/support/static/git-scm.com/book/en/v2/ch00/_personal_avatar.html +0 -858
  381. data/spec/support/static/git-scm.com/book/en/v2/ch00/_plumbing_porcelain.html +0 -745
  382. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_closed.html +0 -1502
  383. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_discussion.html +0 -1502
  384. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_fail.html +0 -1502
  385. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_final.html +0 -1502
  386. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_references.html +0 -1502
  387. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_references_render.html +0 -1502
  388. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pr_refs.html +0 -1218
  389. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pre_merge_rebase_work.html +0 -1028
  390. data/spec/support/static/git-scm.com/book/en/v2/ch00/_preparing_release.html +0 -1354
  391. data/spec/support/static/git-scm.com/book/en/v2/ch00/_private_team.html +0 -1667
  392. data/spec/support/static/git-scm.com/book/en/v2/ch00/_project_over_email.html +0 -1667
  393. data/spec/support/static/git-scm.com/book/en/v2/ch00/_public_project.html +0 -1667
  394. data/spec/support/static/git-scm.com/book/en/v2/ch00/_publishing_submodules.html +0 -1864
  395. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pushing_branches.html +0 -1009
  396. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pushing_refspecs.html +0 -872
  397. data/spec/support/static/git-scm.com/book/en/v2/ch00/_pushing_remotes.html +0 -983
  398. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rebase_cherry_pick.html +0 -1354
  399. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rebase_peril.html +0 -1028
  400. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rebase_rebase.html +0 -1028
  401. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rebase_rebase_work.html +0 -1028
  402. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rebasing.html +0 -1028
  403. data/spec/support/static/git-scm.com/book/en/v2/ch00/_refspec.html +0 -872
  404. data/spec/support/static/git-scm.com/book/en/v2/ch00/_remote_branches.html +0 -1009
  405. data/spec/support/static/git-scm.com/book/en/v2/ch00/_remote_repos.html +0 -983
  406. data/spec/support/static/git-scm.com/book/en/v2/ch00/_removing_file_every_commit.html +0 -1182
  407. data/spec/support/static/git-scm.com/book/en/v2/ch00/_removing_files.html +0 -1432
  408. data/spec/support/static/git-scm.com/book/en/v2/ch00/_removing_objects.html +0 -1086
  409. data/spec/support/static/git-scm.com/book/en/v2/ch00/_replace.html +0 -949
  410. data/spec/support/static/git-scm.com/book/en/v2/ch00/_reverse_commit.html +0 -1605
  411. data/spec/support/static/git-scm.com/book/en/v2/ch00/_revision_selection.html +0 -1178
  412. data/spec/support/static/git-scm.com/book/en/v2/ch00/_rewriting_history.html +0 -1182
  413. data/spec/support/static/git-scm.com/book/en/v2/ch00/_searching.html +0 -875
  414. data/spec/support/static/git-scm.com/book/en/v2/ch00/_service_config.html +0 -1059
  415. data/spec/support/static/git-scm.com/book/en/v2/ch00/_services_hooks.html +0 -1059
  416. data/spec/support/static/git-scm.com/book/en/v2/ch00/_setting_up_server.html +0 -870
  417. data/spec/support/static/git-scm.com/book/en/v2/ch00/_sharing_tags.html +0 -1049
  418. data/spec/support/static/git-scm.com/book/en/v2/ch00/_signing.html +0 -922
  419. data/spec/support/static/git-scm.com/book/en/v2/ch00/_signing_commits.html +0 -922
  420. data/spec/support/static/git-scm.com/book/en/v2/ch00/_squashing.html +0 -1182
  421. data/spec/support/static/git-scm.com/book/en/v2/ch00/_starting_submodules.html +0 -1864
  422. data/spec/support/static/git-scm.com/book/en/v2/ch00/_subtree_merge.html +0 -1605
  423. data/spec/support/static/git-scm.com/book/en/v2/ch00/_switching_branches.html +0 -1020
  424. data/spec/support/static/git-scm.com/book/en/v2/ch00/_tagging_releases.html +0 -1354
  425. data/spec/support/static/git-scm.com/book/en/v2/ch00/_task_list_progress.html +0 -1502
  426. data/spec/support/static/git-scm.com/book/en/v2/ch00/_team_page.html +0 -797
  427. data/spec/support/static/git-scm.com/book/en/v2/ch00/_the_index.html +0 -1236
  428. data/spec/support/static/git-scm.com/book/en/v2/ch00/_the_shortlog.html +0 -1354
  429. data/spec/support/static/git-scm.com/book/en/v2/ch00/_topic_branch.html +0 -786
  430. data/spec/support/static/git-scm.com/book/en/v2/ch00/_tracking_branches.html +0 -1009
  431. data/spec/support/static/git-scm.com/book/en/v2/ch00/_tracking_files.html +0 -1432
  432. data/spec/support/static/git-scm.com/book/en/v2/ch00/_tree_objects.html +0 -1209
  433. data/spec/support/static/git-scm.com/book/en/v2/ch00/_triple_dot.html +0 -1178
  434. data/spec/support/static/git-scm.com/book/en/v2/ch00/_undoing.html +0 -998
  435. data/spec/support/static/git-scm.com/book/en/v2/ch00/_unstaging.html +0 -998
  436. data/spec/support/static/git-scm.com/book/en/v2/ch00/_viewing_history.html +0 -1172
  437. data/spec/support/static/git-scm.com/book/en/v2/ch00/_web_hook.html +0 -1059
  438. data/spec/support/static/git-scm.com/book/en/v2/ch00/_what_is_introduced.html +0 -1354
  439. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch01-getting-started.html +0 -783
  440. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch02-git-basics-chapter.html +0 -816
  441. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch03-git-branching.html +0 -1020
  442. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch05-distributed-git.html +0 -859
  443. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch06-github.html +0 -858
  444. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch06-github_flow.html +0 -1502
  445. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch10-git-internals.html +0 -745
  446. data/spec/support/static/git-scm.com/book/en/v2/ch00/ch_core_editor.html +0 -863
  447. data/spec/support/static/git-scm.com/book/en/v2/ch00/divergent_history.html +0 -1020
  448. data/spec/support/static/git-scm.com/book/en/v2/ch00/double_dot.html +0 -1178
  449. data/spec/support/static/git-scm.com/book/en/v2/ch00/filters_a.html +0 -1134
  450. data/spec/support/static/git-scm.com/book/en/v2/ch00/filters_b.html +0 -1134
  451. data/spec/support/static/git-scm.com/book/en/v2/ch00/limit_options.html +0 -1172
  452. data/spec/support/static/git-scm.com/book/en/v2/ch00/log_options.html +0 -1172
  453. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_a.html +0 -1354
  454. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_b.html +0 -1354
  455. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_c.html +0 -1354
  456. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_d.html +0 -1354
  457. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_e.html +0 -1354
  458. data/spec/support/static/git-scm.com/book/en/v2/ch00/merwf_f.html +0 -1354
  459. data/spec/support/static/git-scm.com/book/en/v2/ch00/oh_my_zsh_git.html +0 -765
  460. data/spec/support/static/git-scm.com/book/en/v2/ch00/pretty_format.html +0 -1172
  461. data/spec/support/static/git-scm.com/book/en/v2/ch00/psp_b.html +0 -1667
  462. data/spec/support/static/git-scm.com/book/en/v2/ch00/rbdiag_e.html +0 -1028
  463. data/spec/support/static/git-scm.com/book/en/v2/ch00/rbdiag_g.html +0 -1028
  464. data/spec/support/static/git-scm.com/book/en/v2/ch00/rbdiag_h.html +0 -1028
  465. data/spec/support/static/git-scm.com/book/en/v2/ch00/rbdiag_i.html +0 -1028
  466. data/spec/support/static/git-scm.com/book/en/v2/ch00/rebasing-merging-example.html +0 -1028
  467. data/spec/support/static/git-scm.com/book/en/v2/ch00/ref_rerere.html +0 -983
  468. data/spec/support/static/git-scm.com/book/en/v2/ch00/ref_the_ref.html +0 -939
  469. data/spec/support/static/git-scm.com/book/en/v2/ch00/wfdiag_b.html +0 -859
  470. data/spec/support/static/git-scm.com/book/en/v2/ch00/wfdiag_c.html +0 -859
  471. data/spec/support/static/git-scm.com/book/en/v2/ch00/what_is_git_section.html +0 -857
  472. data/spec/support/static/git-scm.com/book/en/v2/images/2fa-1.png +0 -0
  473. data/spec/support/static/git-scm.com/book/en/v2/images/account-settings.png +0 -0
  474. data/spec/support/static/git-scm.com/book/en/v2/images/advance-master.png +0 -0
  475. data/spec/support/static/git-scm.com/book/en/v2/images/advance-testing.png +0 -0
  476. data/spec/support/static/git-scm.com/book/en/v2/images/areas.png +0 -0
  477. data/spec/support/static/git-scm.com/book/en/v2/images/avatar-crop.png +0 -0
  478. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-1.png +0 -0
  479. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-2.png +0 -0
  480. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-3.png +0 -0
  481. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-4.png +0 -0
  482. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-5.png +0 -0
  483. data/spec/support/static/git-scm.com/book/en/v2/images/basic-branching-6.png +0 -0
  484. data/spec/support/static/git-scm.com/book/en/v2/images/basic-merging-1.png +0 -0
  485. data/spec/support/static/git-scm.com/book/en/v2/images/basic-merging-2.png +0 -0
  486. data/spec/support/static/git-scm.com/book/en/v2/images/basic-rebase-1.png +0 -0
  487. data/spec/support/static/git-scm.com/book/en/v2/images/basic-rebase-2.png +0 -0
  488. data/spec/support/static/git-scm.com/book/en/v2/images/basic-rebase-3.png +0 -0
  489. data/spec/support/static/git-scm.com/book/en/v2/images/basic-rebase-4.png +0 -0
  490. data/spec/support/static/git-scm.com/book/en/v2/images/benevolent-dictator.png +0 -0
  491. data/spec/support/static/git-scm.com/book/en/v2/images/blink-01-start.png +0 -0
  492. data/spec/support/static/git-scm.com/book/en/v2/images/blink-02-pr.png +0 -0
  493. data/spec/support/static/git-scm.com/book/en/v2/images/blink-03-pull-request-open.png +0 -0
  494. data/spec/support/static/git-scm.com/book/en/v2/images/blink-04-email.png +0 -0
  495. data/spec/support/static/git-scm.com/book/en/v2/images/blink-04-pr-comment.png +0 -0
  496. data/spec/support/static/git-scm.com/book/en/v2/images/blink-05-general-comment.png +0 -0
  497. data/spec/support/static/git-scm.com/book/en/v2/images/blink-06-final.png +0 -0
  498. data/spec/support/static/git-scm.com/book/en/v2/images/branch-and-history.png +0 -0
  499. data/spec/support/static/git-scm.com/book/en/v2/images/branch_widget_mac.png +0 -0
  500. data/spec/support/static/git-scm.com/book/en/v2/images/branch_widget_win.png +0 -0
  501. data/spec/support/static/git-scm.com/book/en/v2/images/centralized.png +0 -0
  502. data/spec/support/static/git-scm.com/book/en/v2/images/centralized_workflow.png +0 -0
  503. data/spec/support/static/git-scm.com/book/en/v2/images/checkout-master.png +0 -0
  504. data/spec/support/static/git-scm.com/book/en/v2/images/clean.png +0 -0
  505. data/spec/support/static/git-scm.com/book/en/v2/images/collaborators.png +0 -0
  506. data/spec/support/static/git-scm.com/book/en/v2/images/commit-and-tree.png +0 -0
  507. data/spec/support/static/git-scm.com/book/en/v2/images/commits-and-parents.png +0 -0
  508. data/spec/support/static/git-scm.com/book/en/v2/images/data-model-1.png +0 -0
  509. data/spec/support/static/git-scm.com/book/en/v2/images/data-model-2.png +0 -0
  510. data/spec/support/static/git-scm.com/book/en/v2/images/data-model-3.png +0 -0
  511. data/spec/support/static/git-scm.com/book/en/v2/images/data-model-4.png +0 -0
  512. data/spec/support/static/git-scm.com/book/en/v2/images/deltas.png +0 -0
  513. data/spec/support/static/git-scm.com/book/en/v2/images/distributed.png +0 -0
  514. data/spec/support/static/git-scm.com/book/en/v2/images/double-dot.png +0 -0
  515. data/spec/support/static/git-scm.com/book/en/v2/images/email-settings.png +0 -0
  516. data/spec/support/static/git-scm.com/book/en/v2/images/forkbutton.png +0 -0
  517. data/spec/support/static/git-scm.com/book/en/v2/images/git-bash.png +0 -0
  518. data/spec/support/static/git-scm.com/book/en/v2/images/git-diff-check.png +0 -0
  519. data/spec/support/static/git-scm.com/book/en/v2/images/git-fusion-boot.png +0 -0
  520. data/spec/support/static/git-scm.com/book/en/v2/images/git-fusion-perforce-graph.png +0 -0
  521. data/spec/support/static/git-scm.com/book/en/v2/images/git-gui.png +0 -0
  522. data/spec/support/static/git-scm.com/book/en/v2/images/git-instaweb.png +0 -0
  523. data/spec/support/static/git-scm.com/book/en/v2/images/git-osx-installer.png +0 -0
  524. data/spec/support/static/git-scm.com/book/en/v2/images/github_mac.png +0 -0
  525. data/spec/support/static/git-scm.com/book/en/v2/images/github_win.png +0 -0
  526. data/spec/support/static/git-scm.com/book/en/v2/images/gitk.png +0 -0
  527. data/spec/support/static/git-scm.com/book/en/v2/images/gitlab-groups.png +0 -0
  528. data/spec/support/static/git-scm.com/book/en/v2/images/gitlab-menu.png +0 -0
  529. data/spec/support/static/git-scm.com/book/en/v2/images/gitlab-users.png +0 -0
  530. data/spec/support/static/git-scm.com/book/en/v2/images/head-to-master.png +0 -0
  531. data/spec/support/static/git-scm.com/book/en/v2/images/head-to-testing.png +0 -0
  532. data/spec/support/static/git-scm.com/book/en/v2/images/integration-manager.png +0 -0
  533. data/spec/support/static/git-scm.com/book/en/v2/images/interesting-rebase-1.png +0 -0
  534. data/spec/support/static/git-scm.com/book/en/v2/images/interesting-rebase-2.png +0 -0
  535. data/spec/support/static/git-scm.com/book/en/v2/images/interesting-rebase-3.png +0 -0
  536. data/spec/support/static/git-scm.com/book/en/v2/images/interesting-rebase-4.png +0 -0
  537. data/spec/support/static/git-scm.com/book/en/v2/images/interesting-rebase-5.png +0 -0
  538. data/spec/support/static/git-scm.com/book/en/v2/images/jb.png +0 -0
  539. data/spec/support/static/git-scm.com/book/en/v2/images/large-merges-1.png +0 -0
  540. data/spec/support/static/git-scm.com/book/en/v2/images/large-merges-2.png +0 -0
  541. data/spec/support/static/git-scm.com/book/en/v2/images/lifecycle.png +0 -0
  542. data/spec/support/static/git-scm.com/book/en/v2/images/local.png +0 -0
  543. data/spec/support/static/git-scm.com/book/en/v2/images/lr-branches-1.png +0 -0
  544. data/spec/support/static/git-scm.com/book/en/v2/images/lr-branches-2.png +0 -0
  545. data/spec/support/static/git-scm.com/book/en/v2/images/maint-01-email.png +0 -0
  546. data/spec/support/static/git-scm.com/book/en/v2/images/maint-02-merge.png +0 -0
  547. data/spec/support/static/git-scm.com/book/en/v2/images/maint-03-email-resp.png +0 -0
  548. data/spec/support/static/git-scm.com/book/en/v2/images/maint-04-target.png +0 -0
  549. data/spec/support/static/git-scm.com/book/en/v2/images/maint-05-mentions.png +0 -0
  550. data/spec/support/static/git-scm.com/book/en/v2/images/maint-06-unsubscribe.png +0 -0
  551. data/spec/support/static/git-scm.com/book/en/v2/images/maint-07-notifications.png +0 -0
  552. data/spec/support/static/git-scm.com/book/en/v2/images/maint-08-notifications-page.png +0 -0
  553. data/spec/support/static/git-scm.com/book/en/v2/images/maint-09-contrib.png +0 -0
  554. data/spec/support/static/git-scm.com/book/en/v2/images/maint-10-default-branch.png +0 -0
  555. data/spec/support/static/git-scm.com/book/en/v2/images/maint-11-transfer.png +0 -0
  556. data/spec/support/static/git-scm.com/book/en/v2/images/managed-team-1.png +0 -0
  557. data/spec/support/static/git-scm.com/book/en/v2/images/managed-team-2.png +0 -0
  558. data/spec/support/static/git-scm.com/book/en/v2/images/managed-team-3.png +0 -0
  559. data/spec/support/static/git-scm.com/book/en/v2/images/managed-team-flow.png +0 -0
  560. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-01-example.png +0 -0
  561. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-02-tasks.png +0 -0
  562. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-03-task-summary.png +0 -0
  563. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-04-fenced-code.png +0 -0
  564. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-05-quote.png +0 -0
  565. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-06-emoji-complete.png +0 -0
  566. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-07-emoji.png +0 -0
  567. data/spec/support/static/git-scm.com/book/en/v2/images/markdown-08-drag-drop.png +0 -0
  568. data/spec/support/static/git-scm.com/book/en/v2/images/mentions-01-syntax.png +0 -0
  569. data/spec/support/static/git-scm.com/book/en/v2/images/mentions-02-render.png +0 -0
  570. data/spec/support/static/git-scm.com/book/en/v2/images/mentions-03-closed.png +0 -0
  571. data/spec/support/static/git-scm.com/book/en/v2/images/merging-workflows-1.png +0 -0
  572. data/spec/support/static/git-scm.com/book/en/v2/images/merging-workflows-2.png +0 -0
  573. data/spec/support/static/git-scm.com/book/en/v2/images/merging-workflows-3.png +0 -0
  574. data/spec/support/static/git-scm.com/book/en/v2/images/merging-workflows-4.png +0 -0
  575. data/spec/support/static/git-scm.com/book/en/v2/images/merging-workflows-5.png +0 -0
  576. data/spec/support/static/git-scm.com/book/en/v2/images/new-repo.png +0 -0
  577. data/spec/support/static/git-scm.com/book/en/v2/images/neworg.png +0 -0
  578. data/spec/support/static/git-scm.com/book/en/v2/images/newrepo.png +0 -0
  579. data/spec/support/static/git-scm.com/book/en/v2/images/newrepoform.png +0 -0
  580. data/spec/support/static/git-scm.com/book/en/v2/images/orgs-01-page.png +0 -0
  581. data/spec/support/static/git-scm.com/book/en/v2/images/orgs-02-teams.png +0 -0
  582. data/spec/support/static/git-scm.com/book/en/v2/images/orgs-03-audit.png +0 -0
  583. data/spec/support/static/git-scm.com/book/en/v2/images/p4merge.png +0 -0
  584. data/spec/support/static/git-scm.com/book/en/v2/images/perils-of-rebasing-1.png +0 -0
  585. data/spec/support/static/git-scm.com/book/en/v2/images/perils-of-rebasing-2.png +0 -0
  586. data/spec/support/static/git-scm.com/book/en/v2/images/perils-of-rebasing-3.png +0 -0
  587. data/spec/support/static/git-scm.com/book/en/v2/images/perils-of-rebasing-4.png +0 -0
  588. data/spec/support/static/git-scm.com/book/en/v2/images/perils-of-rebasing-5.png +0 -0
  589. data/spec/support/static/git-scm.com/book/en/v2/images/posh-git.png +0 -0
  590. data/spec/support/static/git-scm.com/book/en/v2/images/pr-01-fail.png +0 -0
  591. data/spec/support/static/git-scm.com/book/en/v2/images/pr-02-merge-fix.png +0 -0
  592. data/spec/support/static/git-scm.com/book/en/v2/images/public-small-1.png +0 -0
  593. data/spec/support/static/git-scm.com/book/en/v2/images/public-small-2.png +0 -0
  594. data/spec/support/static/git-scm.com/book/en/v2/images/public-small-3.png +0 -0
  595. data/spec/support/static/git-scm.com/book/en/v2/images/rebasing-1.png +0 -0
  596. data/spec/support/static/git-scm.com/book/en/v2/images/rebasing-2.png +0 -0
  597. data/spec/support/static/git-scm.com/book/en/v2/images/remote-branches-1.png +0 -0
  598. data/spec/support/static/git-scm.com/book/en/v2/images/remote-branches-2.png +0 -0
  599. data/spec/support/static/git-scm.com/book/en/v2/images/remote-branches-3.png +0 -0
  600. data/spec/support/static/git-scm.com/book/en/v2/images/remote-branches-4.png +0 -0
  601. data/spec/support/static/git-scm.com/book/en/v2/images/remote-branches-5.png +0 -0
  602. data/spec/support/static/git-scm.com/book/en/v2/images/replace1.png +0 -0
  603. data/spec/support/static/git-scm.com/book/en/v2/images/replace2.png +0 -0
  604. data/spec/support/static/git-scm.com/book/en/v2/images/replace3.png +0 -0
  605. data/spec/support/static/git-scm.com/book/en/v2/images/replace4.png +0 -0
  606. data/spec/support/static/git-scm.com/book/en/v2/images/replace5.png +0 -0
  607. data/spec/support/static/git-scm.com/book/en/v2/images/reposettingslink.png +0 -0
  608. data/spec/support/static/git-scm.com/book/en/v2/images/rerere1.png +0 -0
  609. data/spec/support/static/git-scm.com/book/en/v2/images/rerere2.png +0 -0
  610. data/spec/support/static/git-scm.com/book/en/v2/images/rerere3.png +0 -0
  611. data/spec/support/static/git-scm.com/book/en/v2/images/reset-checkout.png +0 -0
  612. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex1.png +0 -0
  613. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex2.png +0 -0
  614. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex3.png +0 -0
  615. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex4.png +0 -0
  616. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex5.png +0 -0
  617. data/spec/support/static/git-scm.com/book/en/v2/images/reset-ex6.png +0 -0
  618. data/spec/support/static/git-scm.com/book/en/v2/images/reset-hard.png +0 -0
  619. data/spec/support/static/git-scm.com/book/en/v2/images/reset-mixed.png +0 -0
  620. data/spec/support/static/git-scm.com/book/en/v2/images/reset-path1.png +0 -0
  621. data/spec/support/static/git-scm.com/book/en/v2/images/reset-path2.png +0 -0
  622. data/spec/support/static/git-scm.com/book/en/v2/images/reset-path3.png +0 -0
  623. data/spec/support/static/git-scm.com/book/en/v2/images/reset-soft.png +0 -0
  624. data/spec/support/static/git-scm.com/book/en/v2/images/reset-squash-r1.png +0 -0
  625. data/spec/support/static/git-scm.com/book/en/v2/images/reset-squash-r2.png +0 -0
  626. data/spec/support/static/git-scm.com/book/en/v2/images/reset-squash-r3.png +0 -0
  627. data/spec/support/static/git-scm.com/book/en/v2/images/reset-start.png +0 -0
  628. data/spec/support/static/git-scm.com/book/en/v2/images/reset-workflow.png +0 -0
  629. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-01-services.png +0 -0
  630. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-02-email-service.png +0 -0
  631. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-03-webhook.png +0 -0
  632. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-04-webhook-debug.png +0 -0
  633. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-05-access-token.png +0 -0
  634. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-06-comment.png +0 -0
  635. data/spec/support/static/git-scm.com/book/en/v2/images/scripting-07-status.png +0 -0
  636. data/spec/support/static/git-scm.com/book/en/v2/images/signup.png +0 -0
  637. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-1.png +0 -0
  638. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-2.png +0 -0
  639. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-3.png +0 -0
  640. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-4.png +0 -0
  641. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-5.png +0 -0
  642. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-6.png +0 -0
  643. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-7.png +0 -0
  644. data/spec/support/static/git-scm.com/book/en/v2/images/small-team-flow.png +0 -0
  645. data/spec/support/static/git-scm.com/book/en/v2/images/smudge.png +0 -0
  646. data/spec/support/static/git-scm.com/book/en/v2/images/snapshots.png +0 -0
  647. data/spec/support/static/git-scm.com/book/en/v2/images/ssh-keys.png +0 -0
  648. data/spec/support/static/git-scm.com/book/en/v2/images/topic-branches-1.png +0 -0
  649. data/spec/support/static/git-scm.com/book/en/v2/images/topic-branches-2.png +0 -0
  650. data/spec/support/static/git-scm.com/book/en/v2/images/two-branches.png +0 -0
  651. data/spec/support/static/git-scm.com/book/en/v2/images/undomerge-reset.png +0 -0
  652. data/spec/support/static/git-scm.com/book/en/v2/images/undomerge-revert.png +0 -0
  653. data/spec/support/static/git-scm.com/book/en/v2/images/undomerge-revert2.png +0 -0
  654. data/spec/support/static/git-scm.com/book/en/v2/images/undomerge-revert3.png +0 -0
  655. data/spec/support/static/git-scm.com/book/en/v2/images/undomerge-start.png +0 -0
  656. data/spec/support/static/git-scm.com/book/en/v2/images/your-profile.png +0 -0
  657. data/spec/support/static/git-scm.com/book/en/v2/images/zsh-oh-my.png +0 -0
  658. data/spec/support/static/git-scm.com/book/en/v2/images/zsh-prompt.png +0 -0
  659. data/spec/support/static/git-scm.com/book/en/v2.html +0 -688
  660. data/spec/support/static/git-scm.com/favicon.ico +0 -0
  661. data/spec/support/static/git-scm.com/images/bg/body.jpg +0 -0
  662. data/spec/support/static/git-scm.com/images/bg/isometric-grid.png +0 -0
  663. data/spec/support/static/git-scm.com/images/bg/isometric-grid@2x.png +0 -0
  664. data/spec/support/static/git-scm.com/images/bg/search-header.jpg +0 -0
  665. data/spec/support/static/git-scm.com/images/company-project-logos/android.png +0 -0
  666. data/spec/support/static/git-scm.com/images/company-project-logos/android@2x.png +0 -0
  667. data/spec/support/static/git-scm.com/images/company-project-logos/eclipse.png +0 -0
  668. data/spec/support/static/git-scm.com/images/company-project-logos/eclipse@2x.png +0 -0
  669. data/spec/support/static/git-scm.com/images/company-project-logos/facebook.png +0 -0
  670. data/spec/support/static/git-scm.com/images/company-project-logos/facebook@2x.png +0 -0
  671. data/spec/support/static/git-scm.com/images/company-project-logos/gnome.png +0 -0
  672. data/spec/support/static/git-scm.com/images/company-project-logos/gnome@2x.png +0 -0
  673. data/spec/support/static/git-scm.com/images/company-project-logos/google.png +0 -0
  674. data/spec/support/static/git-scm.com/images/company-project-logos/google@2x.png +0 -0
  675. data/spec/support/static/git-scm.com/images/company-project-logos/kde.png +0 -0
  676. data/spec/support/static/git-scm.com/images/company-project-logos/kde@2x.png +0 -0
  677. data/spec/support/static/git-scm.com/images/company-project-logos/linked-in.png +0 -0
  678. data/spec/support/static/git-scm.com/images/company-project-logos/linked-in@2x.png +0 -0
  679. data/spec/support/static/git-scm.com/images/company-project-logos/linux.png +0 -0
  680. data/spec/support/static/git-scm.com/images/company-project-logos/linux@2x.png +0 -0
  681. data/spec/support/static/git-scm.com/images/company-project-logos/microsoft.png +0 -0
  682. data/spec/support/static/git-scm.com/images/company-project-logos/microsoft@2x.png +0 -0
  683. data/spec/support/static/git-scm.com/images/company-project-logos/netflix.png +0 -0
  684. data/spec/support/static/git-scm.com/images/company-project-logos/netflix@2x.png +0 -0
  685. data/spec/support/static/git-scm.com/images/company-project-logos/perl.png +0 -0
  686. data/spec/support/static/git-scm.com/images/company-project-logos/perl@2x.png +0 -0
  687. data/spec/support/static/git-scm.com/images/company-project-logos/postgresql.png +0 -0
  688. data/spec/support/static/git-scm.com/images/company-project-logos/postgresql@2x.png +0 -0
  689. data/spec/support/static/git-scm.com/images/company-project-logos/qt.png +0 -0
  690. data/spec/support/static/git-scm.com/images/company-project-logos/qt@2x.png +0 -0
  691. data/spec/support/static/git-scm.com/images/company-project-logos/rails.png +0 -0
  692. data/spec/support/static/git-scm.com/images/company-project-logos/rails@2x.png +0 -0
  693. data/spec/support/static/git-scm.com/images/company-project-logos/twitter.png +0 -0
  694. data/spec/support/static/git-scm.com/images/company-project-logos/twitter@2x.png +0 -0
  695. data/spec/support/static/git-scm.com/images/company-project-logos/x.png +0 -0
  696. data/spec/support/static/git-scm.com/images/company-project-logos/x@2x.png +0 -0
  697. data/spec/support/static/git-scm.com/images/epub.png +0 -0
  698. data/spec/support/static/git-scm.com/images/icons/admin-sm.png +0 -0
  699. data/spec/support/static/git-scm.com/images/icons/admin-sm@2x.png +0 -0
  700. data/spec/support/static/git-scm.com/images/icons/apple.png +0 -0
  701. data/spec/support/static/git-scm.com/images/icons/apple@2x.png +0 -0
  702. data/spec/support/static/git-scm.com/images/icons/book.png +0 -0
  703. data/spec/support/static/git-scm.com/images/icons/book@2x.png +0 -0
  704. data/spec/support/static/git-scm.com/images/icons/box.png +0 -0
  705. data/spec/support/static/git-scm.com/images/icons/box@2x.png +0 -0
  706. data/spec/support/static/git-scm.com/images/icons/branch-sm.png +0 -0
  707. data/spec/support/static/git-scm.com/images/icons/branch-sm@2x.png +0 -0
  708. data/spec/support/static/git-scm.com/images/icons/camera-sm.png +0 -0
  709. data/spec/support/static/git-scm.com/images/icons/camera-sm@2x.png +0 -0
  710. data/spec/support/static/git-scm.com/images/icons/chevron-up@2x.png +0 -0
  711. data/spec/support/static/git-scm.com/images/icons/code.png +0 -0
  712. data/spec/support/static/git-scm.com/images/icons/code@2x.png +0 -0
  713. data/spec/support/static/git-scm.com/images/icons/debugging-sm.png +0 -0
  714. data/spec/support/static/git-scm.com/images/icons/debugging-sm@2x.png +0 -0
  715. data/spec/support/static/git-scm.com/images/icons/document.png +0 -0
  716. data/spec/support/static/git-scm.com/images/icons/document@2x.png +0 -0
  717. data/spec/support/static/git-scm.com/images/icons/download.png +0 -0
  718. data/spec/support/static/git-scm.com/images/icons/email-sm.png +0 -0
  719. data/spec/support/static/git-scm.com/images/icons/email-sm@2x.png +0 -0
  720. data/spec/support/static/git-scm.com/images/icons/external-sm.png +0 -0
  721. data/spec/support/static/git-scm.com/images/icons/external-sm@2x.png +0 -0
  722. data/spec/support/static/git-scm.com/images/icons/gui.png +0 -0
  723. data/spec/support/static/git-scm.com/images/icons/gui@2x.png +0 -0
  724. data/spec/support/static/git-scm.com/images/icons/info.png +0 -0
  725. data/spec/support/static/git-scm.com/images/icons/info@2x.png +0 -0
  726. data/spec/support/static/git-scm.com/images/icons/inspection-sm.png +0 -0
  727. data/spec/support/static/git-scm.com/images/icons/inspection-sm@2x.png +0 -0
  728. data/spec/support/static/git-scm.com/images/icons/linux.png +0 -0
  729. data/spec/support/static/git-scm.com/images/icons/linux@2x.png +0 -0
  730. data/spec/support/static/git-scm.com/images/icons/nav-circles.png +0 -0
  731. data/spec/support/static/git-scm.com/images/icons/nav-circles@2x.png +0 -0
  732. data/spec/support/static/git-scm.com/images/icons/patching-sm.png +0 -0
  733. data/spec/support/static/git-scm.com/images/icons/patching-sm@2x.png +0 -0
  734. data/spec/support/static/git-scm.com/images/icons/plumbing-sm.png +0 -0
  735. data/spec/support/static/git-scm.com/images/icons/plumbing-sm@2x.png +0 -0
  736. data/spec/support/static/git-scm.com/images/icons/projects-sm.png +0 -0
  737. data/spec/support/static/git-scm.com/images/icons/projects-sm@2x.png +0 -0
  738. data/spec/support/static/git-scm.com/images/icons/search.png +0 -0
  739. data/spec/support/static/git-scm.com/images/icons/search@2x.png +0 -0
  740. data/spec/support/static/git-scm.com/images/icons/server-admin-sm.png +0 -0
  741. data/spec/support/static/git-scm.com/images/icons/server-admin-sm@2x.png +0 -0
  742. data/spec/support/static/git-scm.com/images/icons/setup-sm.png +0 -0
  743. data/spec/support/static/git-scm.com/images/icons/setup-sm@2x.png +0 -0
  744. data/spec/support/static/git-scm.com/images/icons/sharing-sm.png +0 -0
  745. data/spec/support/static/git-scm.com/images/icons/sharing-sm@2x.png +0 -0
  746. data/spec/support/static/git-scm.com/images/icons/sidebar.png +0 -0
  747. data/spec/support/static/git-scm.com/images/icons/sidebar@2x.png +0 -0
  748. data/spec/support/static/git-scm.com/images/icons/source-code.png +0 -0
  749. data/spec/support/static/git-scm.com/images/icons/source-code@2x.png +0 -0
  750. data/spec/support/static/git-scm.com/images/icons/windows.png +0 -0
  751. data/spec/support/static/git-scm.com/images/icons/windows@2x.png +0 -0
  752. data/spec/support/static/git-scm.com/images/logo@2x.png +0 -0
  753. data/spec/support/static/git-scm.com/images/mobi.png +0 -0
  754. data/spec/support/static/git-scm.com/images/monitor-default.png +0 -0
  755. data/spec/support/static/git-scm.com/images/monitor-default@2x.png +0 -0
  756. data/spec/support/static/git-scm.com/images/monitor-linux.png +0 -0
  757. data/spec/support/static/git-scm.com/images/monitor-linux@2x.png +0 -0
  758. data/spec/support/static/git-scm.com/images/monitor-mac.png +0 -0
  759. data/spec/support/static/git-scm.com/images/monitor-mac@2x.png +0 -0
  760. data/spec/support/static/git-scm.com/images/monitor-windows.png +0 -0
  761. data/spec/support/static/git-scm.com/images/monitor-windows@2x.png +0 -0
  762. data/spec/support/static/git-scm.com/images/pdf.png +0 -0
  763. data/spec/support/static/git-scm.com/images/progit2.png +0 -0
  764. data/spec/support/static/git-scm.com/images/sidebar-divider.png +0 -0
  765. data/spec/support/static/git-scm.com/images/sidebar-divider@2x.png +0 -0
  766. data/spec/support/static/git-scm.com/robots.txt +0 -0
  767. data/spec/support/static/graph/details/a.html +0 -10
  768. data/spec/support/static/graph/details/b.html +0 -10
  769. data/spec/support/static/graph/index.html +0 -20
  770. data/spec/support/static/links/links.html +0 -28
  771. data/docs/{reference → guides}/cli.md +0 -0
  772. data/spec/{stringify_spec.rb → wayfarer/stringify_spec.rb} +2 -2
  773. /data/spec/{task_spec.rb → wayfarer/task_spec.rb} +0 -0
@@ -1,1200 +0,0 @@
1
- <!DOCTYPE html>
2
- <html lang="en">
3
-
4
- <head>
5
- <!-- Global site tag (gtag.js) - Google Analytics -->
6
- <script async src="https://www.googletagmanager.com/gtag/js?id=UA-49925874-3"></script>
7
- <script>
8
- window.dataLayer = window.dataLayer || [];
9
- function gtag(){dataLayer.push(arguments);}
10
- gtag('js', new Date());
11
-
12
- gtag('config', 'UA-49925874-3');
13
- </script>
14
-
15
- <meta charset='utf-8'>
16
- <meta content='IE=edge,chrome=1' http-equiv='X-UA-Compatible'>
17
- <meta name="viewport" content="width=device-width, initial-scale=1">
18
- <title>Git - An Example Git-Enforced Policy</title>
19
-
20
- <link href='../../../../favicon.ico' rel='shortcut icon' type='image/x-icon'>
21
-
22
- <link rel="stylesheet" media="screen" href="../../../../assets/application-cafcf280f67db0e6d8168ba98a38da878769a9d5f37793b68ffb963a02d185e0.css" />
23
- <script src="../../../../assets/modernize-b3ebe0c31c24f230dc62179d3e1030d2e57a53b1668d9382c0a27dbd44a94beb.js"></script>
24
- <!--[if (gte IE 6)&(lte IE 8)]>
25
- <script src="/javascripts/selectivizr-min.js"></script>
26
- <![endif]-->
27
-
28
- </head>
29
-
30
- <body id="documentation">
31
-
32
- <div class="inner">
33
- <header>
34
-
35
- <a href="https://git-scm.com/"><img src="../../../../images/logo@2x.png" width="110" height="46" alt="Git" /></a>
36
- <span id="tagline"></span>
37
- <script type="text/javascript">
38
- var taglines = ["fast-version-control","everything-is-local","distributed-even-if-your-workflow-isnt","local-branching-on-the-cheap","distributed-is-the-new-centralized"];
39
- var tagline = taglines[Math.floor(Math.random() * taglines.length)];
40
- document.getElementById('tagline').innerHTML = '--' + tagline;
41
- </script>
42
- <form id="search" action="https://git-scm.com/search/results">
43
- <input id="search-text" name="search" placeholder="Search entire site..." autocomplete="off" type="text" />
44
- </form>
45
- <div id="search-results"></div>
46
-
47
- </header>
48
-
49
- </div> <!-- .inner -->
50
-
51
- <div class="inner">
52
- <div id="content-wrapper">
53
- <button class="sidebar-btn"></button>
54
- <aside class="sidebar" id="sidebar">
55
- <nav>
56
- <ul>
57
- <li>
58
- <a href="https://git-scm.com/about">About</a>
59
- <ul class="">
60
- <li>
61
- <a href="https://git-scm.com/about">Branching and Merging</a>
62
- </li>
63
- <li>
64
- <a href="https://git-scm.com/about/small-and-fast">Small and Fast</a>
65
- </li>
66
- <li>
67
- <a href="https://git-scm.com/about/distributed">Distributed</a>
68
- </li>
69
- <li>
70
- <a href="https://git-scm.com/about/info-assurance">Data Assurance</a>
71
- </li>
72
- <li>
73
- <a href="https://git-scm.com/about/staging-area">Staging Area</a>
74
- </li>
75
- <li>
76
- <a href="https://git-scm.com/about/free-and-open-source">Free and Open Source</a>
77
- </li>
78
- <li>
79
- <a href="https://git-scm.com/about/trademark">Trademark</a>
80
- </li>
81
- </ul>
82
- </li>
83
- <li>
84
- <a class="active" href="https://git-scm.com/doc">Documentation</a>
85
- <ul class="expanded">
86
- <li>
87
- <a href="https://git-scm.com/docs">Reference</a>
88
- </li>
89
- <li>
90
- <a class="active" href="https://git-scm.com/book">Book</a>
91
- </li>
92
- <li>
93
- <a href="https://git-scm.com/videos">Videos</a>
94
- </li>
95
- <li>
96
- <a href="https://git-scm.com/doc/ext">External Links</a>
97
- </li>
98
- </ul>
99
- </li>
100
- <li>
101
- <a href="https://git-scm.com/downloads">Downloads</a>
102
- <ul class="">
103
- <li>
104
- <a href="https://git-scm.com/downloads/guis">GUI Clients</a>
105
- </li>
106
- <li>
107
- <a href="https://git-scm.com/downloads/logos">Logos</a>
108
- </li>
109
- </ul>
110
- </li>
111
- <li>
112
- <a href="https://git-scm.com/community">Community</a>
113
- </li>
114
- </ul>
115
- <hr class="sidebar">
116
- <p>
117
- This book is available in
118
- <a href="https://git-scm.com/book/en">English</a>.
119
- </p>
120
- <p>
121
- Full translation available in
122
- <table>
123
- <tr><td><a href="https://git-scm.com/book/az">azərbaycan dili</a>,</td></tr>
124
- <tr><td><a href="https://git-scm.com/book/bg">български език</a>,</td></tr>
125
- <tr><td><a href="https://git-scm.com/book/de">Deutsch</a>,</td></tr>
126
- <tr><td><a href="https://git-scm.com/book/es">Español</a>,</td></tr>
127
- <tr><td><a href="https://git-scm.com/book/fr">Français</a>,</td></tr>
128
- <tr><td><a href="https://git-scm.com/book/gr">Ελληνικά</a>,</td></tr>
129
- <tr><td><a href="https://git-scm.com/book/ja">日本語</a>,</td></tr>
130
- <tr><td><a href="https://git-scm.com/book/ko">한국어</a>,</td></tr>
131
- <tr><td><a href="https://git-scm.com/book/nl">Nederlands</a>,</td></tr>
132
- <tr><td><a href="https://git-scm.com/book/ru">Русский</a>,</td></tr>
133
- <tr><td><a href="https://git-scm.com/book/sl">Slovenščina</a>,</td></tr>
134
- <tr><td><a href="https://git-scm.com/book/tl">Tagalog</a>,</td></tr>
135
- <tr><td><a href="https://git-scm.com/book/uk">Українська</a></td></tr>
136
- <tr><td><a href="https://git-scm.com/book/zh">简体中文</a>,</td></tr>
137
- </table>
138
- </p>
139
- <p>
140
- Partial translations available in
141
- <table>
142
- <tr><td><a href="https://git-scm.com/book/cs">Čeština</a>,</td></tr>
143
- <tr><td><a href="https://git-scm.com/book/mk">Македонски</a>,</td></tr>
144
- <tr><td><a href="https://git-scm.com/book/pl">Polski</a>,</td></tr>
145
- <tr><td><a href="https://git-scm.com/book/sr">Српски</a>,</td></tr>
146
- <tr><td><a href="https://git-scm.com/book/uz">Ўзбекча</a>,</td></tr>
147
- <tr><td><a href="https://git-scm.com/book/zh-tw">繁體中文</a>,</td></tr>
148
- </table>
149
- </p>
150
- <p>
151
- Translations started for
152
- <table>
153
- <tr><td><a href="https://git-scm.com/book/be">Беларуская</a>,</td></tr>
154
- <tr><td><a href="https://git-scm.com/book/fa" dir="rtl">فارسی</a>,</td></tr>
155
- <tr><td><a href="https://git-scm.com/book/id">Indonesian</a>,</td></tr>
156
- <tr><td><a href="https://git-scm.com/book/it">Italiano</a>,</td></tr>
157
- <tr><td><a href="https://git-scm.com/book/ms">Bahasa Melayu</a>,</td></tr>
158
- <tr><td><a href="https://git-scm.com/book/pt-br">Português (Brasil)</a>,</td></tr>
159
- <tr><td><a href="https://git-scm.com/book/pt-pt">Português (Portugal)</a>,</td></tr>
160
- <tr><td><a href="https://git-scm.com/book/sv">Svenska</a>,</td></tr>
161
- <tr><td><a href="https://git-scm.com/book/tr">Türkçe</a>.</td></tr>
162
- </table>
163
- </p>
164
- <hr class="sidebar"/>
165
- <p>
166
- The source of this book is <a href="https://github.com/progit/progit2">hosted on GitHub.</a></br>
167
- Patches, suggestions and comments are welcome.
168
- </p>
169
-
170
-
171
- </nav>
172
- </aside>
173
-
174
- <div id="content">
175
-
176
-
177
- <div id='book-chapters'>
178
- <a class="dropdown-trigger" id="book-chapters-trigger" data-panel-id="chapters-dropdown" href="_enforcing_commit_message_format.html#">Chapters ▾</a>
179
- <div class='dropdown-panel' id='chapters-dropdown'>
180
- <div class="three-column">
181
- <div class='column-left'>
182
- <ol class='book-toc'>
183
- <li class='chapter'>
184
- <h2>1. <a href="ch01-getting-started.html">Getting Started</a></h2>
185
- <ol>
186
- <li>
187
- 1.1
188
- <a href="ch01-getting-started.html" >About Version Control </a>
189
- </li>
190
- <li>
191
- 1.2
192
- <a href="../Getting-Started-A-Short-History-of-Git.html" >A Short History of Git </a>
193
- </li>
194
- <li>
195
- 1.3
196
- <a href="what_is_git_section.html" >What is Git? </a>
197
- </li>
198
- <li>
199
- 1.4
200
- <a href="../Getting-Started-The-Command-Line.html" >The Command Line </a>
201
- </li>
202
- <li>
203
- 1.5
204
- <a href="../Getting-Started-Installing-Git.html" >Installing Git </a>
205
- </li>
206
- <li>
207
- 1.6
208
- <a href="_editor.html" >First-Time Git Setup </a>
209
- </li>
210
- <li>
211
- 1.7
212
- <a href="_git_help.html" >Getting Help </a>
213
- </li>
214
- <li>
215
- 1.8
216
- <a href="../Getting-Started-Summary.html" >Summary </a>
217
- </li>
218
- </ol>
219
- </li>
220
- <li class='chapter'>
221
- <h2>2. <a href="_git_cloning.html">Git Basics</a></h2>
222
- <ol>
223
- <li>
224
- 2.1
225
- <a href="_git_cloning.html" >Getting a Git Repository </a>
226
- </li>
227
- <li>
228
- 2.2
229
- <a href="_git_mv.html" >Recording Changes to the Repository </a>
230
- </li>
231
- <li>
232
- 2.3
233
- <a href="_viewing_history.html" >Viewing the Commit History </a>
234
- </li>
235
- <li>
236
- 2.4
237
- <a href="_unstaging.html" >Undoing Things </a>
238
- </li>
239
- <li>
240
- 2.5
241
- <a href="_remote_repos.html" >Working with Remotes </a>
242
- </li>
243
- <li>
244
- 2.6
245
- <a href="_annotated_tags.html" >Tagging </a>
246
- </li>
247
- <li>
248
- 2.7
249
- <a href="_git_aliases.html" >Git Aliases </a>
250
- </li>
251
- <li>
252
- 2.8
253
- <a href="../Git-Basics-Summary.html" >Summary </a>
254
- </li>
255
- </ol>
256
- </li>
257
- <li class='chapter'>
258
- <h2>3. <a href="_switching_branches.html">Git Branching</a></h2>
259
- <ol>
260
- <li>
261
- 3.1
262
- <a href="_switching_branches.html" >Branches in a Nutshell </a>
263
- </li>
264
- <li>
265
- 3.2
266
- <a href="_basic_branching.html" >Basic Branching and Merging </a>
267
- </li>
268
- <li>
269
- 3.3
270
- <a href="_branch_management.html" >Branch Management </a>
271
- </li>
272
- <li>
273
- 3.4
274
- <a href="_topic_branch.html" >Branching Workflows </a>
275
- </li>
276
- <li>
277
- 3.5
278
- <a href="_delete_branches.html" >Remote Branches </a>
279
- </li>
280
- <li>
281
- 3.6
282
- <a href="_rebase_rebase.html" >Rebasing </a>
283
- </li>
284
- <li>
285
- 3.7
286
- <a href="../Git-Branching-Summary.html" >Summary </a>
287
- </li>
288
- </ol>
289
- </li>
290
- <li class='chapter'>
291
- <h2>4. <a href="../Git-on-the-Server-The-Protocols.html">Git on the Server</a></h2>
292
- <ol>
293
- <li>
294
- 4.1
295
- <a href="../Git-on-the-Server-The-Protocols.html" >The Protocols </a>
296
- </li>
297
- <li>
298
- 4.2
299
- <a href="_bare_repo.html" >Getting Git on a Server </a>
300
- </li>
301
- <li>
302
- 4.3
303
- <a href="_generate_ssh_key.html" >Generating Your SSH Public Key </a>
304
- </li>
305
- <li>
306
- 4.4
307
- <a href="_setting_up_server.html" >Setting Up the Server </a>
308
- </li>
309
- <li>
310
- 4.5
311
- <a href="../Git-on-the-Server-Git-Daemon.html" >Git Daemon </a>
312
- </li>
313
- <li>
314
- 4.6
315
- <a href="../Git-on-the-Server-Smart-HTTP.html" >Smart HTTP </a>
316
- </li>
317
- <li>
318
- 4.7
319
- <a href="../Git-on-the-Server-GitWeb.html" >GitWeb </a>
320
- </li>
321
- <li>
322
- 4.8
323
- <a href="_gitlab_groups_section.html" >GitLab </a>
324
- </li>
325
- <li>
326
- 4.9
327
- <a href="../Git-on-the-Server-Third-Party-Hosted-Options.html" >Third Party Hosted Options </a>
328
- </li>
329
- <li>
330
- 4.10
331
- <a href="../Git-on-the-Server-Summary.html" >Summary </a>
332
- </li>
333
- </ol>
334
- </li>
335
- <li class='chapter'>
336
- <h2>5. <a href="_integration_manager.html">Distributed Git</a></h2>
337
- <ol>
338
- <li>
339
- 5.1
340
- <a href="_integration_manager.html" >Distributed Workflows </a>
341
- </li>
342
- <li>
343
- 5.2
344
- <a href="_project_over_email.html" >Contributing to a Project </a>
345
- </li>
346
- <li>
347
- 5.3
348
- <a href="_git_am.html" >Maintaining a Project </a>
349
- </li>
350
- <li>
351
- 5.4
352
- <a href="../Distributed-Git-Summary.html" >Summary </a>
353
- </li>
354
- </ol>
355
- </li>
356
- </ol>
357
-
358
- </div>
359
- <div class='column-middle'>
360
- <ol class='book-toc'>
361
- <li class='chapter'>
362
- <h2>6. <a href="_personal_avatar.html">GitHub</a></h2>
363
- <ol>
364
- <li>
365
- 6.1
366
- <a href="_personal_avatar.html" >Account Setup and Configuration </a>
367
- </li>
368
- <li>
369
- 6.2
370
- <a href="_fetch_and_push_on_different_repositories.html" >Contributing to a Project </a>
371
- </li>
372
- <li>
373
- 6.3
374
- <a href="_email_notifications.html" >Maintaining a Project </a>
375
- </li>
376
- <li>
377
- 6.4
378
- <a href="_team_page.html" >Managing an organization </a>
379
- </li>
380
- <li>
381
- 6.5
382
- <a href="_commit_status.html" >Scripting GitHub </a>
383
- </li>
384
- <li>
385
- 6.6
386
- <a href="../GitHub-Summary.html" >Summary </a>
387
- </li>
388
- </ol>
389
- </li>
390
- <li class='chapter'>
391
- <h2>7. <a href="_git_reflog.html">Git Tools</a></h2>
392
- <ol>
393
- <li>
394
- 7.1
395
- <a href="_git_reflog.html" >Revision Selection </a>
396
- </li>
397
- <li>
398
- 7.2
399
- <a href="_interactive_staging.html" >Interactive Staging </a>
400
- </li>
401
- <li>
402
- 7.3
403
- <a href="_git_clean.html" >Stashing and Cleaning </a>
404
- </li>
405
- <li>
406
- 7.4
407
- <a href="_signing_commits.html" >Signing Your Work </a>
408
- </li>
409
- <li>
410
- 7.5
411
- <a href="_git_grep.html" >Searching </a>
412
- </li>
413
- <li>
414
- 7.6
415
- <a href="_removing_file_every_commit.html" >Rewriting History </a>
416
- </li>
417
- <li>
418
- 7.7
419
- <a href="_the_index.html" >Reset Demystified </a>
420
- </li>
421
- <li>
422
- 7.8
423
- <a href="_reverse_commit.html" >Advanced Merging </a>
424
- </li>
425
- <li>
426
- 7.9
427
- <a href="ref_rerere.html" >Rerere </a>
428
- </li>
429
- <li>
430
- 7.10
431
- <a href="_file_annotation.html" >Debugging with Git </a>
432
- </li>
433
- <li>
434
- 7.11
435
- <a href="_publishing_submodules.html" >Submodules </a>
436
- </li>
437
- <li>
438
- 7.12
439
- <a href="_bundling.html" >Bundling </a>
440
- </li>
441
- <li>
442
- 7.13
443
- <a href="_replace.html" >Replace </a>
444
- </li>
445
- <li>
446
- 7.14
447
- <a href="_credential_caching.html" >Credential Storage </a>
448
- </li>
449
- <li>
450
- 7.15
451
- <a href="../Git-Tools-Summary.html" >Summary </a>
452
- </li>
453
- </ol>
454
- </li>
455
- <li class='chapter'>
456
- <h2>8. <a href="_external_merge_tools.html">Customizing Git</a></h2>
457
- <ol>
458
- <li>
459
- 8.1
460
- <a href="_external_merge_tools.html" >Git Configuration </a>
461
- </li>
462
- <li>
463
- 8.2
464
- <a href="_keyword_expansion.html" >Git Attributes </a>
465
- </li>
466
- <li>
467
- 8.3
468
- <a href="_email_hooks.html" >Git Hooks </a>
469
- </li>
470
- <li>
471
- 8.4
472
- <a href="_enforcing_commit_message_format.html" class=active>An Example Git-Enforced Policy </a>
473
- </li>
474
- <li>
475
- 8.5
476
- <a href="../Customizing-Git-Summary.html" >Summary </a>
477
- </li>
478
- </ol>
479
- </li>
480
- <li class='chapter'>
481
- <h2>9. <a href="_git_svn.html">Git and Other Systems</a></h2>
482
- <ol>
483
- <li>
484
- 9.1
485
- <a href="_git_svn.html" >Git as a Client </a>
486
- </li>
487
- <li>
488
- 9.2
489
- <a href="_git_p4.html" >Migrating to Git </a>
490
- </li>
491
- <li>
492
- 9.3
493
- <a href="../Git-and-Other-Systems-Summary.html" >Summary </a>
494
- </li>
495
- </ol>
496
- </li>
497
- <li class='chapter'>
498
- <h2>10. <a href="_plumbing_porcelain.html">Git Internals</a></h2>
499
- <ol>
500
- <li>
501
- 10.1
502
- <a href="_plumbing_porcelain.html" >Plumbing and Porcelain </a>
503
- </li>
504
- <li>
505
- 10.2
506
- <a href="_git_commit_objects.html" >Git Objects </a>
507
- </li>
508
- <li>
509
- 10.3
510
- <a href="ref_the_ref.html" >Git References </a>
511
- </li>
512
- <li>
513
- 10.4
514
- <a href="../Git-Internals-Packfiles.html" >Packfiles </a>
515
- </li>
516
- <li>
517
- 10.5
518
- <a href="_pushing_refspecs.html" >The Refspec </a>
519
- </li>
520
- <li>
521
- 10.6
522
- <a href="../Git-Internals-Transfer-Protocols.html" >Transfer Protocols </a>
523
- </li>
524
- <li>
525
- 10.7
526
- <a href="_git_gc.html" >Maintenance and Data Recovery </a>
527
- </li>
528
- <li>
529
- 10.8
530
- <a href="../Git-Internals-Environment-Variables.html" >Environment Variables </a>
531
- </li>
532
- <li>
533
- 10.9
534
- <a href="../Git-Internals-Summary.html" >Summary </a>
535
- </li>
536
- </ol>
537
- </li>
538
- </ol>
539
-
540
- </div>
541
- <div class='column-right'>
542
- <ol class='book-toc'>
543
- <li class='chapter'>
544
- <h2>A1. <a href="../Appendix-A:-Git-in-Other-Environments-Graphical-Interfaces.html">Appendix A: Git in Other Environments</a></h2>
545
- <ol>
546
- <li>
547
- A1.1
548
- <a href="../Appendix-A:-Git-in-Other-Environments-Graphical-Interfaces.html" >Graphical Interfaces </a>
549
- </li>
550
- <li>
551
- A1.2
552
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-Visual-Studio.html" >Git in Visual Studio </a>
553
- </li>
554
- <li>
555
- A1.3
556
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-Visual-Studio-Code.html" >Git in Visual Studio Code </a>
557
- </li>
558
- <li>
559
- A1.4
560
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-IntelliJ-%252F-PyCharm-%252F-WebStorm-%252F-PhpStorm-%252F-RubyMine.html" >Git in IntelliJ / PyCharm / WebStorm / PhpStorm / RubyMine </a>
561
- </li>
562
- <li>
563
- A1.5
564
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-Sublime-Text.html" >Git in Sublime Text </a>
565
- </li>
566
- <li>
567
- A1.6
568
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-Bash.html" >Git in Bash </a>
569
- </li>
570
- <li>
571
- A1.7
572
- <a href="oh_my_zsh_git.html" >Git in Zsh </a>
573
- </li>
574
- <li>
575
- A1.8
576
- <a href="../Appendix-A:-Git-in-Other-Environments-Git-in-PowerShell.html" >Git in PowerShell </a>
577
- </li>
578
- <li>
579
- A1.9
580
- <a href="../Appendix-A:-Git-in-Other-Environments-Summary.html" >Summary </a>
581
- </li>
582
- </ol>
583
- </li>
584
- <li class='chapter'>
585
- <h2>A2. <a href="../Appendix-B:-Embedding-Git-in-your-Applications-Command-line-Git.html">Appendix B: Embedding Git in your Applications</a></h2>
586
- <ol>
587
- <li>
588
- A2.1
589
- <a href="../Appendix-B:-Embedding-Git-in-your-Applications-Command-line-Git.html" >Command-line Git </a>
590
- </li>
591
- <li>
592
- A2.2
593
- <a href="_libgit2_bindings.html" >Libgit2 </a>
594
- </li>
595
- <li>
596
- A2.3
597
- <a href="../Appendix-B:-Embedding-Git-in-your-Applications-JGit.html" >JGit </a>
598
- </li>
599
- <li>
600
- A2.4
601
- <a href="../Appendix-B:-Embedding-Git-in-your-Applications-go-git.html" >go-git </a>
602
- </li>
603
- <li>
604
- A2.5
605
- <a href="../Appendix-B:-Embedding-Git-in-your-Applications-Dulwich.html" >Dulwich </a>
606
- </li>
607
- </ol>
608
- </li>
609
- <li class='chapter'>
610
- <h2>A3. <a href="ch_core_editor.html">Appendix C: Git Commands</a></h2>
611
- <ol>
612
- <li>
613
- A3.1
614
- <a href="ch_core_editor.html" >Setup and Config </a>
615
- </li>
616
- <li>
617
- A3.2
618
- <a href="../Appendix-C:-Git-Commands-Getting-and-Creating-Projects.html" >Getting and Creating Projects </a>
619
- </li>
620
- <li>
621
- A3.3
622
- <a href="../Appendix-C:-Git-Commands-Basic-Snapshotting.html" >Basic Snapshotting </a>
623
- </li>
624
- <li>
625
- A3.4
626
- <a href="../Appendix-C:-Git-Commands-Branching-and-Merging.html" >Branching and Merging </a>
627
- </li>
628
- <li>
629
- A3.5
630
- <a href="../Appendix-C:-Git-Commands-Sharing-and-Updating-Projects.html" >Sharing and Updating Projects </a>
631
- </li>
632
- <li>
633
- A3.6
634
- <a href="../Appendix-C:-Git-Commands-Inspection-and-Comparison.html" >Inspection and Comparison </a>
635
- </li>
636
- <li>
637
- A3.7
638
- <a href="../Appendix-C:-Git-Commands-Debugging.html" >Debugging </a>
639
- </li>
640
- <li>
641
- A3.8
642
- <a href="../Appendix-C:-Git-Commands-Patching.html" >Patching </a>
643
- </li>
644
- <li>
645
- A3.9
646
- <a href="../Appendix-C:-Git-Commands-Email.html" >Email </a>
647
- </li>
648
- <li>
649
- A3.10
650
- <a href="../Appendix-C:-Git-Commands-External-Systems.html" >External Systems </a>
651
- </li>
652
- <li>
653
- A3.11
654
- <a href="../Appendix-C:-Git-Commands-Administration.html" >Administration </a>
655
- </li>
656
- <li>
657
- A3.12
658
- <a href="../Appendix-C:-Git-Commands-Plumbing-Commands.html" >Plumbing Commands </a>
659
- </li>
660
- </ol>
661
- </li>
662
- </ol>
663
-
664
- </div>
665
- </div>
666
- </div>
667
-
668
- <span class="light" id="edition">
669
- 2nd Edition
670
- </span>
671
- </div>
672
-
673
- <div id='main' class="book edition2">
674
- <h1>8.4 Customizing Git - An Example Git-Enforced Policy</h1>
675
- <div>
676
- <h2 id="_an_example_git_enforced_policy">An Example Git-Enforced Policy</h2>
677
- <div class="paragraph">
678
- <p>
679
- In this section, you’ll use what you’ve learned to establish a Git workflow that checks for a custom commit message format, and allows only certain users to modify certain subdirectories in a project.
680
- You’ll build client scripts that help the developer know if their push will be rejected and server scripts that actually enforce the policies.</p>
681
- </div>
682
- <div class="paragraph">
683
- <p>The scripts we’ll show are written in Ruby; partly because of our intellectual inertia, but also because Ruby is easy to read, even if you can’t necessarily write it.
684
- However, any language will work – all the sample hook scripts distributed with Git are in either Perl or Bash, so you can also see plenty of examples of hooks in those languages by looking at the samples.</p>
685
- </div>
686
- <div class="sect3">
687
- <h3 id="_server_side_hook">Server-Side Hook</h3>
688
- <div class="paragraph">
689
- <p>All the server-side work will go into the <code>update</code> file in your <code>hooks</code> directory.
690
- The <code>update</code> hook runs once per branch being pushed and takes three arguments:</p>
691
- </div>
692
- <div class="ulist">
693
- <ul>
694
- <li>
695
- <p>The name of the reference being pushed to</p>
696
- </li>
697
- <li>
698
- <p>The old revision where that branch was</p>
699
- </li>
700
- <li>
701
- <p>The new revision being pushed</p>
702
- </li>
703
- </ul>
704
- </div>
705
- <div class="paragraph">
706
- <p>You also have access to the user doing the pushing if the push is being run over SSH.
707
- If you’ve allowed everyone to connect with a single user (like “git”) via public-key authentication, you may have to give that user a shell wrapper that determines which user is connecting based on the public key, and set an environment variable accordingly.
708
- Here we’ll assume the connecting user is in the <code>$USER</code> environment variable, so your update script begins by gathering all the information you need:</p>
709
- </div>
710
- <div class="listingblock">
711
- <div class="content">
712
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">#!/usr/bin/env ruby
713
-
714
- $refname = ARGV[0]
715
- $oldrev = ARGV[1]
716
- $newrev = ARGV[2]
717
- $user = ENV['USER']
718
-
719
- puts "Enforcing Policies..."
720
- puts "(#{$refname}) (#{$oldrev[0,6]}) (#{$newrev[0,6]})"</code></pre>
721
- </div>
722
- </div>
723
- <div class="paragraph">
724
- <p>Yes, those are global variables.
725
- Don’t judge – it’s easier to demonstrate this way.</p>
726
- </div>
727
- <div class="sect4">
728
- <h4 id="_enforcing_commit_message_format">Enforcing a Specific Commit-Message Format</h4>
729
- <div class="paragraph">
730
- <p>Your first challenge is to enforce that each commit message adheres to a particular format.
731
- Just to have a target, assume that each message has to include a string that looks like “ref: 1234” because you want each commit to link to a work item in your ticketing system.
732
- You must look at each commit being pushed up, see if that string is in the commit message, and, if the string is absent from any of the commits, exit non-zero so the push is rejected.</p>
733
- </div>
734
- <div class="paragraph">
735
- <p>You can get a list of the SHA-1 values of all the commits that are being pushed by taking the <code>$newrev</code> and <code>$oldrev</code> values and passing them to a Git plumbing command called <code>git rev-list</code>.
736
- This is basically the <code>git log</code> command, but by default it prints out only the SHA-1 values and no other information.
737
- So, to get a list of all the commit SHA-1s introduced between one commit SHA-1 and another, you can run something like this:</p>
738
- </div>
739
- <div class="listingblock">
740
- <div class="content">
741
- <pre class="highlight"><code class="language-console" data-lang="console">$ git rev-list 538c33..d14fc7
742
- d14fc7c847ab946ec39590d87783c69b031bdfb7
743
- 9f585da4401b0a3999e84113824d15245c13f0be
744
- 234071a1be950e2a8d078e6141f5cd20c1e61ad3
745
- dfa04c9ef3d5197182f13fb5b9b1fb7717d2222a
746
- 17716ec0f1ff5c77eff40b7fe912f9f6cfd0e475</code></pre>
747
- </div>
748
- </div>
749
- <div class="paragraph">
750
- <p>You can take that output, loop through each of those commit SHA-1s, grab the message for it, and test that message against a regular expression that looks for a pattern.</p>
751
- </div>
752
- <div class="paragraph">
753
- <p>You have to figure out how to get the commit message from each of these commits to test.
754
- To get the raw commit data, you can use another plumbing command called <code>git cat-file</code>.
755
- We’ll go over all these plumbing commands in detail in <a href="ch10-git-internals.html">Git Internals</a>; but for now, here’s what that command gives you:</p>
756
- </div>
757
- <div class="listingblock">
758
- <div class="content">
759
- <pre class="highlight"><code class="language-console" data-lang="console">$ git cat-file commit ca82a6
760
- tree cfda3bf379e4f8dba8717dee55aab78aef7f4daf
761
- parent 085bb3bcb608e1e8451d4b2432f8ecbe6306e7e7
762
- author Scott Chacon &lt;schacon@gmail.com&gt; 1205815931 -0700
763
- committer Scott Chacon &lt;schacon@gmail.com&gt; 1240030591 -0700
764
-
765
- Change the version number</code></pre>
766
- </div>
767
- </div>
768
- <div class="paragraph">
769
- <p>A simple way to get the commit message from a commit when you have the SHA-1 value is to go to the first blank line and take everything after that.
770
- You can do so with the <code>sed</code> command on Unix systems:</p>
771
- </div>
772
- <div class="listingblock">
773
- <div class="content">
774
- <pre class="highlight"><code class="language-console" data-lang="console">$ git cat-file commit ca82a6 | sed '1,/^$/d'
775
- Change the version number</code></pre>
776
- </div>
777
- </div>
778
- <div class="paragraph">
779
- <p>You can use that incantation to grab the commit message from each commit that is trying to be pushed and exit if you see anything that doesn’t match.
780
- To exit the script and reject the push, exit non-zero.
781
- The whole method looks like this:</p>
782
- </div>
783
- <div class="listingblock">
784
- <div class="content">
785
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">$regex = /\[ref: (\d+)\]/
786
-
787
- # enforced custom commit message format
788
- def check_message_format
789
- missed_revs = `git rev-list #{$oldrev}..#{$newrev}`.split("\n")
790
- missed_revs.each do |rev|
791
- message = `git cat-file commit #{rev} | sed '1,/^$/d'`
792
- if !$regex.match(message)
793
- puts "[POLICY] Your message is not formatted correctly"
794
- exit 1
795
- end
796
- end
797
- end
798
- check_message_format</code></pre>
799
- </div>
800
- </div>
801
- <div class="paragraph">
802
- <p>Putting that in your <code>update</code> script will reject updates that contain commits that have messages that don’t adhere to your rule.</p>
803
- </div>
804
- </div>
805
- <div class="sect4">
806
- <h4 id="_enforcing_a_user_based_acl_system">Enforcing a User-Based ACL System</h4>
807
- <div class="paragraph">
808
- <p>Suppose you want to add a mechanism that uses an access control list (ACL) that specifies which users are allowed to push changes to which parts of your projects.
809
- Some people have full access, and others can only push changes to certain subdirectories or specific files.
810
- To enforce this, you’ll write those rules to a file named <code>acl</code> that lives in your bare Git repository on the server.
811
- You’ll have the <code>update</code> hook look at those rules, see what files are being introduced for all the commits being pushed, and determine whether the user doing the push has access to update all those files.</p>
812
- </div>
813
- <div class="paragraph">
814
- <p>The first thing you’ll do is write your ACL.
815
- Here you’ll use a format very much like the CVS ACL mechanism: it uses a series of lines, where the first field is <code>avail</code> or <code>unavail</code>, the next field is a comma-delimited list of the users to which the rule applies, and the last field is the path to which the rule applies (blank meaning open access).
816
- All of these fields are delimited by a pipe (<code>|</code>) character.</p>
817
- </div>
818
- <div class="paragraph">
819
- <p>In this case, you have a couple of administrators, some documentation writers with access to the <code>doc</code> directory, and one developer who only has access to the <code>lib</code> and <code>tests</code> directories, and your ACL file looks like this:</p>
820
- </div>
821
- <div class="listingblock">
822
- <div class="content">
823
- <pre class="highlight"><code>avail|nickh,pjhyett,defunkt,tpw
824
- avail|usinclair,cdickens,ebronte|doc
825
- avail|schacon|lib
826
- avail|schacon|tests</code></pre>
827
- </div>
828
- </div>
829
- <div class="paragraph">
830
- <p>You begin by reading this data into a structure that you can use.
831
- In this case, to keep the example simple, you’ll only enforce the <code>avail</code> directives.
832
- Here is a method that gives you an associative array where the key is the user name and the value is an array of paths to which the user has write access:</p>
833
- </div>
834
- <div class="listingblock">
835
- <div class="content">
836
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">def get_acl_access_data(acl_file)
837
- # read in ACL data
838
- acl_file = File.read(acl_file).split("\n").reject { |line| line == '' }
839
- access = {}
840
- acl_file.each do |line|
841
- avail, users, path = line.split('|')
842
- next unless avail == 'avail'
843
- users.split(',').each do |user|
844
- access[user] ||= []
845
- access[user] &lt;&lt; path
846
- end
847
- end
848
- access
849
- end</code></pre>
850
- </div>
851
- </div>
852
- <div class="paragraph">
853
- <p>On the ACL file you looked at earlier, this <code>get_acl_access_data</code> method returns a data structure that looks like this:</p>
854
- </div>
855
- <div class="listingblock">
856
- <div class="content">
857
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">{"defunkt"=&gt;[nil],
858
- "tpw"=&gt;[nil],
859
- "nickh"=&gt;[nil],
860
- "pjhyett"=&gt;[nil],
861
- "schacon"=&gt;["lib", "tests"],
862
- "cdickens"=&gt;["doc"],
863
- "usinclair"=&gt;["doc"],
864
- "ebronte"=&gt;["doc"]}</code></pre>
865
- </div>
866
- </div>
867
- <div class="paragraph">
868
- <p>Now that you have the permissions sorted out, you need to determine what paths the commits being pushed have modified, so you can make sure the user who’s pushing has access to all of them.</p>
869
- </div>
870
- <div class="paragraph">
871
- <p>You can pretty easily see what files have been modified in a single commit with the <code>--name-only</code> option to the <code>git log</code> command (mentioned briefly in <a href="ch02-git-basics-chapter.html">Git Basics</a>):</p>
872
- </div>
873
- <div class="listingblock">
874
- <div class="content">
875
- <pre class="highlight"><code class="language-console" data-lang="console">$ git log -1 --name-only --pretty=format:'' 9f585d
876
-
877
- README
878
- lib/test.rb</code></pre>
879
- </div>
880
- </div>
881
- <div class="paragraph">
882
- <p>If you use the ACL structure returned from the <code>get_acl_access_data</code> method and check it against the listed files in each of the commits, you can determine whether the user has access to push all of their commits:</p>
883
- </div>
884
- <div class="listingblock">
885
- <div class="content">
886
- <pre class="highlight"><code class="language-ruby" data-lang="ruby"># only allows certain users to modify certain subdirectories in a project
887
- def check_directory_perms
888
- access = get_acl_access_data('acl')
889
-
890
- # see if anyone is trying to push something they can't
891
- new_commits = `git rev-list #{$oldrev}..#{$newrev}`.split("\n")
892
- new_commits.each do |rev|
893
- files_modified = `git log -1 --name-only --pretty=format:'' #{rev}`.split("\n")
894
- files_modified.each do |path|
895
- next if path.size == 0
896
- has_file_access = false
897
- access[$user].each do |access_path|
898
- if !access_path # user has access to everything
899
- || (path.start_with? access_path) # access to this path
900
- has_file_access = true
901
- end
902
- end
903
- if !has_file_access
904
- puts "[POLICY] You do not have access to push to #{path}"
905
- exit 1
906
- end
907
- end
908
- end
909
- end
910
-
911
- check_directory_perms</code></pre>
912
- </div>
913
- </div>
914
- <div class="paragraph">
915
- <p>You get a list of new commits being pushed to your server with <code>git rev-list</code>.
916
- Then, for each of those commits, you find which files are modified and make sure the user who’s pushing has access to all the paths being modified.</p>
917
- </div>
918
- <div class="paragraph">
919
- <p>Now your users can’t push any commits with badly formed messages or with modified files outside of their designated paths.</p>
920
- </div>
921
- </div>
922
- <div class="sect4">
923
- <h4 id="_testing_it_out">Testing It Out</h4>
924
- <div class="paragraph">
925
- <p>If you run <code>chmod u+x .git/hooks/update</code>, which is the file into which you should have put all this code, and then try to push a commit with a non-compliant message, you get something like this:</p>
926
- </div>
927
- <div class="listingblock">
928
- <div class="content">
929
- <pre class="highlight"><code class="language-console" data-lang="console">$ git push -f origin master
930
- Counting objects: 5, done.
931
- Compressing objects: 100% (3/3), done.
932
- Writing objects: 100% (3/3), 323 bytes, done.
933
- Total 3 (delta 1), reused 0 (delta 0)
934
- Unpacking objects: 100% (3/3), done.
935
- Enforcing Policies...
936
- (refs/heads/master) (8338c5) (c5b616)
937
- [POLICY] Your message is not formatted correctly
938
- error: hooks/update exited with error code 1
939
- error: hook declined to update refs/heads/master
940
- To git@gitserver:project.git
941
- ! [remote rejected] master -&gt; master (hook declined)
942
- error: failed to push some refs to 'git@gitserver:project.git'</code></pre>
943
- </div>
944
- </div>
945
- <div class="paragraph">
946
- <p>There are a couple of interesting things here.
947
- First, you see this where the hook starts running.</p>
948
- </div>
949
- <div class="listingblock">
950
- <div class="content">
951
- <pre class="highlight"><code class="language-console" data-lang="console">Enforcing Policies...
952
- (refs/heads/master) (fb8c72) (c56860)</code></pre>
953
- </div>
954
- </div>
955
- <div class="paragraph">
956
- <p>Remember that you printed that out at the very beginning of your update script.
957
- Anything your script echoes to <code>stdout</code> will be transferred to the client.</p>
958
- </div>
959
- <div class="paragraph">
960
- <p>The next thing you’ll notice is the error message.</p>
961
- </div>
962
- <div class="listingblock">
963
- <div class="content">
964
- <pre class="highlight"><code class="language-console" data-lang="console">[POLICY] Your message is not formatted correctly
965
- error: hooks/update exited with error code 1
966
- error: hook declined to update refs/heads/master</code></pre>
967
- </div>
968
- </div>
969
- <div class="paragraph">
970
- <p>The first line was printed out by you, the other two were Git telling you that the update script exited non-zero and that is what is declining your push.
971
- Lastly, you have this:</p>
972
- </div>
973
- <div class="listingblock">
974
- <div class="content">
975
- <pre class="highlight"><code class="language-console" data-lang="console">To git@gitserver:project.git
976
- ! [remote rejected] master -&gt; master (hook declined)
977
- error: failed to push some refs to 'git@gitserver:project.git'</code></pre>
978
- </div>
979
- </div>
980
- <div class="paragraph">
981
- <p>You’ll see a remote rejected message for each reference that your hook declined, and it tells you that it was declined specifically because of a hook failure.</p>
982
- </div>
983
- <div class="paragraph">
984
- <p>Furthermore, if someone tries to edit a file they don’t have access to and push a commit containing it, they will see something similar.
985
- For instance, if a documentation author tries to push a commit modifying something in the <code>lib</code> directory, they see:</p>
986
- </div>
987
- <div class="listingblock">
988
- <div class="content">
989
- <pre class="highlight"><code class="language-console" data-lang="console">[POLICY] You do not have access to push to lib/test.rb</code></pre>
990
- </div>
991
- </div>
992
- <div class="paragraph">
993
- <p>From now on, as long as that <code>update</code> script is there and executable, your repository will never have a commit message without your pattern in it, and your users will be sandboxed.</p>
994
- </div>
995
- </div>
996
- </div>
997
- <div class="sect3">
998
- <h3 id="_client_side_hooks_2">Client-Side Hooks</h3>
999
- <div class="paragraph">
1000
- <p>The downside to this approach is the whining that will inevitably result when your users' commit pushes are rejected.
1001
- Having their carefully crafted work rejected at the last minute can be extremely frustrating and confusing; and furthermore, they will have to edit their history to correct it, which isn’t always for the faint of heart.</p>
1002
- </div>
1003
- <div class="paragraph">
1004
- <p>The answer to this dilemma is to provide some client-side hooks that users can run to notify them when they’re doing something that the server is likely to reject.
1005
- That way, they can correct any problems before committing and before those issues become more difficult to fix.
1006
- Because hooks aren’t transferred with a clone of a project, you must distribute these scripts some other way and then have your users copy them to their <code>.git/hooks</code> directory and make them executable.
1007
- You can distribute these hooks within the project or in a separate project, but Git won’t set them up automatically.</p>
1008
- </div>
1009
- <div class="paragraph">
1010
- <p>To begin, you should check your commit message just before each commit is recorded, so you know the server won’t reject your changes due to badly formatted commit messages.
1011
- To do this, you can add the <code>commit-msg</code> hook.
1012
- If you have it read the message from the file passed as the first argument and compare that to the pattern, you can force Git to abort the commit if there is no match:</p>
1013
- </div>
1014
- <div class="listingblock">
1015
- <div class="content">
1016
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">#!/usr/bin/env ruby
1017
- message_file = ARGV[0]
1018
- message = File.read(message_file)
1019
-
1020
- $regex = /\[ref: (\d+)\]/
1021
-
1022
- if !$regex.match(message)
1023
- puts "[POLICY] Your message is not formatted correctly"
1024
- exit 1
1025
- end</code></pre>
1026
- </div>
1027
- </div>
1028
- <div class="paragraph">
1029
- <p>If that script is in place (in <code>.git/hooks/commit-msg</code>) and executable, and you commit with a message that isn’t properly formatted, you see this:</p>
1030
- </div>
1031
- <div class="listingblock">
1032
- <div class="content">
1033
- <pre class="highlight"><code class="language-console" data-lang="console">$ git commit -am 'Test'
1034
- [POLICY] Your message is not formatted correctly</code></pre>
1035
- </div>
1036
- </div>
1037
- <div class="paragraph">
1038
- <p>No commit was completed in that instance.
1039
- However, if your message contains the proper pattern, Git allows you to commit:</p>
1040
- </div>
1041
- <div class="listingblock">
1042
- <div class="content">
1043
- <pre class="highlight"><code class="language-console" data-lang="console">$ git commit -am 'Test [ref: 132]'
1044
- [master e05c914] Test [ref: 132]
1045
- 1 file changed, 1 insertions(+), 0 deletions(-)</code></pre>
1046
- </div>
1047
- </div>
1048
- <div class="paragraph">
1049
- <p>Next, you want to make sure you aren’t modifying files that are outside your ACL scope.
1050
- If your project’s <code>.git</code> directory contains a copy of the ACL file you used previously, then the following <code>pre-commit</code> script will enforce those constraints for you:</p>
1051
- </div>
1052
- <div class="listingblock">
1053
- <div class="content">
1054
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">#!/usr/bin/env ruby
1055
-
1056
- $user = ENV['USER']
1057
-
1058
- # [ insert acl_access_data method from above ]
1059
-
1060
- # only allows certain users to modify certain subdirectories in a project
1061
- def check_directory_perms
1062
- access = get_acl_access_data('.git/acl')
1063
-
1064
- files_modified = `git diff-index --cached --name-only HEAD`.split("\n")
1065
- files_modified.each do |path|
1066
- next if path.size == 0
1067
- has_file_access = false
1068
- access[$user].each do |access_path|
1069
- if !access_path || (path.index(access_path) == 0)
1070
- has_file_access = true
1071
- end
1072
- if !has_file_access
1073
- puts "[POLICY] You do not have access to push to #{path}"
1074
- exit 1
1075
- end
1076
- end
1077
- end
1078
-
1079
- check_directory_perms</code></pre>
1080
- </div>
1081
- </div>
1082
- <div class="paragraph">
1083
- <p>This is roughly the same script as the server-side part, but with two important differences.
1084
- First, the ACL file is in a different place, because this script runs from your working directory, not from your <code>.git</code> directory.
1085
- You have to change the path to the ACL file from this:</p>
1086
- </div>
1087
- <div class="listingblock">
1088
- <div class="content">
1089
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">access = get_acl_access_data('acl')</code></pre>
1090
- </div>
1091
- </div>
1092
- <div class="paragraph">
1093
- <p>to this:</p>
1094
- </div>
1095
- <div class="listingblock">
1096
- <div class="content">
1097
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">access = get_acl_access_data('.git/acl')</code></pre>
1098
- </div>
1099
- </div>
1100
- <div class="paragraph">
1101
- <p>The other important difference is the way you get a listing of the files that have been changed.
1102
- Because the server-side method looks at the log of commits, and, at this point, the commit hasn’t been recorded yet, you must get your file listing from the staging area instead.
1103
- Instead of:</p>
1104
- </div>
1105
- <div class="listingblock">
1106
- <div class="content">
1107
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">files_modified = `git log -1 --name-only --pretty=format:'' #{ref}`</code></pre>
1108
- </div>
1109
- </div>
1110
- <div class="paragraph">
1111
- <p>you have to use:</p>
1112
- </div>
1113
- <div class="listingblock">
1114
- <div class="content">
1115
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">files_modified = `git diff-index --cached --name-only HEAD`</code></pre>
1116
- </div>
1117
- </div>
1118
- <div class="paragraph">
1119
- <p>But those are the only two differences – otherwise, the script works the same way.
1120
- One caveat is that it expects you to be running locally as the same user you push as to the remote machine.
1121
- If that is different, you must set the <code>$user</code> variable manually.</p>
1122
- </div>
1123
- <div class="paragraph">
1124
- <p>One other thing we can do here is make sure the user doesn’t push non-fast-forwarded references.
1125
- To get a reference that isn’t a fast-forward, you either have to rebase past a commit you’ve already pushed up or try pushing a different local branch up to the same remote branch.</p>
1126
- </div>
1127
- <div class="paragraph">
1128
- <p>Presumably, the server is already configured with <code>receive.denyDeletes</code> and <code>receive.denyNonFastForwards</code> to enforce this policy, so the only accidental thing you can try to catch is rebasing commits that have already been pushed.</p>
1129
- </div>
1130
- <div class="paragraph">
1131
- <p>Here is an example pre-rebase script that checks for that.
1132
- It gets a list of all the commits you’re about to rewrite and checks whether they exist in any of your remote references.
1133
- If it sees one that is reachable from one of your remote references, it aborts the rebase.</p>
1134
- </div>
1135
- <div class="listingblock">
1136
- <div class="content">
1137
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">#!/usr/bin/env ruby
1138
-
1139
- base_branch = ARGV[0]
1140
- if ARGV[1]
1141
- topic_branch = ARGV[1]
1142
- else
1143
- topic_branch = "HEAD"
1144
- end
1145
-
1146
- target_shas = `git rev-list #{base_branch}..#{topic_branch}`.split("\n")
1147
- remote_refs = `git branch -r`.split("\n").map { |r| r.strip }
1148
-
1149
- target_shas.each do |sha|
1150
- remote_refs.each do |remote_ref|
1151
- shas_pushed = `git rev-list ^#{sha}^@ refs/remotes/#{remote_ref}`
1152
- if shas_pushed.split("\n").include?(sha)
1153
- puts "[POLICY] Commit #{sha} has already been pushed to #{remote_ref}"
1154
- exit 1
1155
- end
1156
- end
1157
- end</code></pre>
1158
- </div>
1159
- </div>
1160
- <div class="paragraph">
1161
- <p>This script uses a syntax that wasn’t covered in <a href="_revision_selection.html">Revision Selection</a>.
1162
- You get a list of commits that have already been pushed up by running this:</p>
1163
- </div>
1164
- <div class="listingblock">
1165
- <div class="content">
1166
- <pre class="highlight"><code class="language-ruby" data-lang="ruby">`git rev-list ^#{sha}^@ refs/remotes/#{remote_ref}`</code></pre>
1167
- </div>
1168
- </div>
1169
- <div class="paragraph">
1170
- <p>The <code>SHA^@</code> syntax resolves to all the parents of that commit.
1171
- You’re looking for any commit that is reachable from the last commit on the remote and that isn’t reachable from any parent of any of the SHA-1s you’re trying to push up – meaning it’s a fast-forward.</p>
1172
- </div>
1173
- <div class="paragraph">
1174
- <p>The main drawback to this approach is that it can be very slow and is often unnecessary – if you don’t try to force the push with <code>-f</code>, the server will warn you and not accept the push.
1175
- However, it’s an interesting exercise and can in theory help you avoid a rebase that you might later have to go back and fix.</p>
1176
- </div>
1177
- </div>
1178
- <div id="nav"><a href="_email_hooks.html">prev</a> | <a href="../Customizing-Git-Summary.html">next</a></div></div>
1179
- </div>
1180
-
1181
- </div>
1182
- </div>
1183
- <footer>
1184
- <div class="site-source">
1185
- <a href="https://git-scm.com/site">About this site</a><br>
1186
- Patches, suggestions, and comments are welcome.
1187
- </div>
1188
- <div class="sfc-member">
1189
- Git is a member of <a href="https://git-scm.com/sfc">Software Freedom Conservancy</a>
1190
- </div>
1191
- </footer>
1192
- <a href="_enforcing_commit_message_format.html#top" class="no-js scrollToTop" id="scrollToTop" data-label="Scroll to top">
1193
- <img src="../../../../images/icons/chevron-up@2x.png" width="20" height="20" alt="scroll-to-top"/>
1194
- </a>
1195
- <script src="../../../../assets/application-38b0d42ff05ffea45841edebbd14b75b89585646153808e82907c2c5c11f324b.js"></script>
1196
-
1197
- </div>
1198
-
1199
- </body>
1200
- </html>