diff --git a/app/models/repository.rb b/app/models/repository.rb index aeec48ee5cc82e40c249494621ae6bb1aeb9298b..0f262d2ecbb13170f931c882fd8062af568e0799 100644 --- a/app/models/repository.rb +++ b/app/models/repository.rb @@ -151,3 +151,4 @@ class Repository super end end + diff --git a/doc/api/repositories.md b/doc/api/repositories.md index cb0626972e5a20720a3b53c3a638de54a42030b9..d0499ee7fd66478795237eac492ad947393cd8ef 100644 --- a/doc/api/repositories.md +++ b/doc/api/repositories.md @@ -39,6 +39,66 @@ Parameters: ] ``` +## Create a branch + +Create a new branch. + +``` +POST /projects/:id/repository/branches/:branch/:ref +``` + +Parameters: ++ `id` (required) - The ID of the project ++ `:branch` (required) - The name of the branch being created ++ `:ref` (required) - Reference branch is built from (Branch/Tag/SHA1/etc) + +```json +{ + "name": "test_branch", + "commit": { + "id": "d67868df74c26c88b2cf1d25d91a269f237963e8", + "parents": [ + { + "id": "ccd7a20d618558b2ac17d49200500de01e6adce1" + }, + { + "id": "de60b9aa1c2c66f4cb7c76541e01a15ebdef0838" + } + ], + "tree": "90b63cf2244f93d0b3eef162dc05f8c94f3527ec", + "message": "Merge pull request #1249 from braddunbar/throttle\n\nPrevent false negatives for _.throttle tests.", + "author": { + "name": "Jeremy Ashkenas", + "email": "jashkenas@gmail.com" + }, + "committer": { + "name": "Jeremy Ashkenas", + "email": "jashkenas@gmail.com" + }, + "authored_date": "2013-08-07T15:35:30+00:00", + "committed_date": "2013-08-07T15:35:30+00:00" + }, + "protected": false +} +``` + +## Delete a branch + +Delete a new branch. + +``` +DELETE /projects/:id/repository/branches/:branch +``` + +Parameters: ++ `id` (required) - The ID of the project ++ `:branch` (required) - The name of the branch being deleted + +```json +{ + "success": true +} +``` ## Get single repository branch @@ -80,6 +140,67 @@ Parameters: } ``` +## Create a tag + +Create a new tag. + +``` +POST /projects/:id/repository/tags/:tag/:ref +``` + +Parameters: ++ `id` (required) - The ID of the project ++ `:tag` (required) - The name of the tag being created ++ `:ref` (required) - Reference tag is built from (Branch/Tag/SHA1/etc) + +```json +{ + "name": "v1.1", + "commit": { + "id": "d67868df74c26c88b2cf1d25d91a269f237963e8", + "parents": [ + { + "id": "ccd7a20d618558b2ac17d49200500de01e6adce1" + }, + { + "id": "de60b9aa1c2c66f4cb7c76541e01a15ebdef0838" + } + ], + "tree": "90b63cf2244f93d0b3eef162dc05f8c94f3527ec", + "message": "Merge pull request #1249 from braddunbar/throttle\n\nPrevent false negatives for _.throttle tests.", + "author": { + "name": "Jeremy Ashkenas", + "email": "jashkenas@gmail.com" + }, + "committer": { + "name": "Jeremy Ashkenas", + "email": "jashkenas@gmail.com" + }, + "authored_date": "2013-08-07T15:35:30+00:00", + "committed_date": "2013-08-07T15:35:30+00:00" + }, + "protected": false +} +``` + +## Delete a tag + +Delete a new tag. + +``` +DELETE /projects/:id/repository/tags/:tag +``` + +Parameters: ++ `id` (required) - The ID of the project ++ `:tag` (required) - The name of the tag being deleted + +```json +{ + "success": true +} +``` + ## Protect repository branch diff --git a/lib/api/helpers.rb b/lib/api/helpers.rb index 4f189f3519672e651a48a49a6cffafdbc7984a23..462f3d124989c8fa40a14df5512b24eede4a2b06 100644 --- a/lib/api/helpers.rb +++ b/lib/api/helpers.rb @@ -110,6 +110,10 @@ module API render_api_error!('401 Unauthorized', 401) end + def resource_exists! + render_api_error!('Resource Already Exists', 409) + end + def not_allowed! render_api_error!('Method Not Allowed', 405) end diff --git a/lib/api/repositories.rb b/lib/api/repositories.rb index fef32d3a2fe5893971c24fc3b927858a1b466383..1b42cdc9f66928769d2ced268166a3e8cbe313af 100644 --- a/lib/api/repositories.rb +++ b/lib/api/repositories.rb @@ -23,6 +23,43 @@ module API present user_project.repo.heads.sort_by(&:name), with: Entities::RepoObject, project: user_project end + + # Create a branch + # + # Parameters: + # id (required) - The ID of a project + # branch (required) - The name of the branch + # ref (required) - SHA1 ref of branch. + # Example Request: + # POST /projects/:id/repository/branches/:branch/:ref + post ":id/repository/branches/:branch/:ref", + :requirements => { :branch => /.*/, :ref => /.*/ } do + + @branch = user_project.repo.heads.find { |item| item.name == params[:branch] } + resource_exists! if @branch + + user_project.repository.add_branch(params[:branch], params[:ref]) + @branch = user_project.repo.heads.find { |item| item.name == params[:branch] } + + present @branch, with: Entities::RepoObject, project: user_project + end + + # Deletes a branch + # + # Parameters: + # id (required) - The ID of a project + # branch (required) - The name of the branch + # Example Request: + # DELETE /projects/:id/repository/branches/:branch + delete ":id/repository/branches/:branch", + :requirements => { :branch => /.*/ } do + @branch = user_project.repo.heads.find { |item| item.name == params[:branch] } + not_found! unless @branch + + user_project.repository.rm_branch(params[:branch]) + present({ 'success' => true }) + end + # Get a single branch # # Parameters: @@ -84,6 +121,41 @@ module API present user_project.repo.tags.sort_by(&:name).reverse, with: Entities::RepoObject end + # Create a tag + # + # Parameters: + # id (required) - The ID of a project + # tag (required) - The name of the tag + # ref (required) - SHA1 ref of tag. + # Example Request: + # POST /projects/:id/repository/tags/:tag/:ref + post ":id/repository/tags/:tag/:ref", + :requirements => { :tag => /.*/, :ref => /.*/ } do + @tag = user_project.repo.tags.find { |item| item.name == params[:tag] } + resource_exists! if @tag + + user_project.repository.add_tag(params[:tag], params[:ref]) + @tag = user_project.repo.tags.find { |item| item.name == params[:tag] } + + present @tag, with: Entities::RepoObject, project: user_project + end + + # Deletes a tag + # + # Parameters: + # id (required) - The ID of a project + # tag (required) - The name of the tag + # Example Request: + # DELETE /projects/:id/repository/tags/:tag + delete ":id/repository/tags/:tag", + :requirements => { :tag => /.*/ } do + @tag = user_project.repo.tags.find { |item| item.name == params[:tag] } + not_found! unless @tag + + user_project.repository.rm_tag(params[:tag]) + present({ 'success' => true }) + end + # Get a project repository commits # # Parameters: diff --git a/lib/gitlab/backend/shell.rb b/lib/gitlab/backend/shell.rb index c819ce56ac91319c6cb745a66f108ed3619781fe..114fa44c145e204a4ebb87d5caa3e4a372898b45 100644 --- a/lib/gitlab/backend/shell.rb +++ b/lib/gitlab/backend/shell.rb @@ -217,3 +217,4 @@ module Gitlab end end end + diff --git a/spec/requests/api/repositories_spec.rb b/spec/requests/api/repositories_spec.rb index f15abdd358106595d163a9b6d3eb940a5ec1734b..e4954effc5d320f91fef09bc4363211c787d4d66 100644 --- a/spec/requests/api/repositories_spec.rb +++ b/spec/requests/api/repositories_spec.rb @@ -38,6 +38,50 @@ describe API::API do end end + describe "POST /projects/:id/repository/branches/:branch/:ref" do + it "should return that the request was received" do + post api("/projects/#{project.id}/repository/branches/new_branch/master", user) + response.status.should == 201 + end + + it "should return a 409 conflict if the resource already exists" do + post api("/projects/#{project.id}/repository/branches/new_design/master", user) + response.status.should == 409 + end + end + + describe "DELETE /projects/:id/repository/branches/:branch/" do + it "should return that the request was received" do + delete api("/projects/#{project.id}/repository/branches/master", user) + response.status.should == 200 + + json_response['success'].should == true + end + + it "should return a 404 not found if the resource already exists" do + delete api("/projects/#{project.id}/repository/branches/abranchthatdoesnotexist", user) + response.status.should == 404 + end + end + + describe "POST /projects/:id/repository/tags/:tag/:ref" do + it "should return that the request was received" do + post api("/projects/#{project.id}/repository/tags/v1.0/master", user) + response.status.should == 201 + end + it "should return a 409 conflict if the resource already exists" do + post api("/projects/#{project.id}/repository/tags/v0.9.4/master", user) + response.status.should == 409 + end + end + + describe "DELETE /projects/:id/repository/tags/:tag/" do + it "should return a 404 not found if the resource already exists" do + delete api("/projects/#{project.id}/repository/tags/atagthatdoesnotexist", user) + response.status.should == 404 + end + end + describe "PUT /projects/:id/repository/branches/:branch/protect" do it "should protect a single branch" do put api("/projects/#{project.id}/repository/branches/new_design/protect", user)