ghup 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. data/README.md +14 -0
  2. data/bin/ghup +113 -0
  3. metadata +64 -0
data/README.md ADDED
@@ -0,0 +1,14 @@
1
+ This is a script which can upload files to github from the commandline.
2
+
3
+ First you need to get a oauth token:
4
+
5
+ curl -X POST -u <github user>:<github password> \
6
+ -d '{"note":"file upload script","scopes":["repo"]}' \
7
+ https://api.github.com/authorizations
8
+
9
+ Copy the token from the response and put it into your git config file:
10
+
11
+ git config --global github.upload-script-token <the token from the response>
12
+
13
+
14
+ Now you can use this script.
data/bin/ghup ADDED
@@ -0,0 +1,113 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'json'
4
+ require 'net/https'
5
+ require 'pathname'
6
+
7
+
8
+
9
+ # Extensions
10
+ # ----------
11
+
12
+ # We extend Pathname a bit to get the content type.
13
+ class Pathname
14
+ def type
15
+ flags = RUBY_PLATFORM =~ /darwin/ ? 'Ib' : 'ib'
16
+ `file -#{flags} #{realpath}`.chomp.gsub(/;.*/,'')
17
+ end
18
+ end
19
+
20
+
21
+
22
+ # Helpers
23
+ # -------
24
+
25
+ # Die if something goes wrong.
26
+ def die(msg); puts(msg); exit!(1); end
27
+
28
+ # Do a post to the given url, with the payload and optional basic auth.
29
+ def post(url, token, params, headers)
30
+ uri = URI.parse(url)
31
+
32
+ http = Net::HTTP.new(uri.host, uri.port)
33
+ http.use_ssl = true
34
+
35
+ req = Net::HTTP::Post.new(uri.path, headers)
36
+ req['Authorization'] = "token #{token}" if token
37
+
38
+ return http.request(req, params)
39
+ end
40
+
41
+ def urlencode(str)
42
+ str.gsub(/[^a-zA-Z0-9_\.\-]/n) {|s| sprintf('%%%02x', s[0].to_i) }
43
+ end
44
+
45
+ # Yep, ruby net/http doesn't support multipart. Write our own multipart generator.
46
+ # The order of the params is important, the file needs to go as last!
47
+ def build_multipart_content(params)
48
+ parts, boundary = [], "#{rand(1000000)}-we-are-all-doomed-#{rand(1000000)}"
49
+
50
+ params.each do |name, value|
51
+ data = []
52
+ if value.is_a?(Pathname) then
53
+ data << "Content-Disposition: form-data; name=\"#{urlencode(name.to_s)}\"; filename=\"#{value.basename}\""
54
+ data << "Content-Type: #{value.type}"
55
+ data << "Content-Length: #{value.size}"
56
+ data << "Content-Transfer-Encoding: binary"
57
+ data << ""
58
+ data << value.read
59
+ else
60
+ data << "Content-Disposition: form-data; name=\"#{urlencode(name.to_s)}\""
61
+ data << ""
62
+ data << value
63
+ end
64
+
65
+ parts << data.join("\r\n") + "\r\n"
66
+ end
67
+
68
+ [ "--#{boundary}\r\n" + parts.join("--#{boundary}\r\n") + "--#{boundary}--", {
69
+ "Content-Type" => "multipart/form-data; boundary=#{boundary}"
70
+ }]
71
+ end
72
+
73
+
74
+
75
+ # Configuration and setup
76
+ # -----------------------
77
+
78
+ # Get Oauth token for this script.
79
+ token = `git config --get github.upload-script-token`.chomp
80
+
81
+ # The file we want to upload, and repo where to upload it to.
82
+ file = Pathname.new(ARGV[0])
83
+ repo = ARGV[1] || `git config --get remote.origin.url`.match(/git@github.com:(.+?)\.git/)[1]
84
+
85
+
86
+
87
+ # The actual, hard work
88
+ # ---------------------
89
+
90
+ # Register the download at github.
91
+ res = post("https://api.github.com/repos/#{repo}/downloads", token, {
92
+ 'name' => file.basename.to_s, 'size' => file.size.to_s,
93
+ 'content_type' => file.type.gsub(/;.*/, '')
94
+ }.to_json, {})
95
+
96
+ die("File already exists.") if res.class == Net::HTTPClientError
97
+ die("GitHub doens't want us to upload the file.") unless res.class == Net::HTTPCreated
98
+
99
+
100
+ # Parse the body and use the info to upload the file to S3.
101
+ info = JSON.parse(res.body)
102
+ res = post(info['s3_url'], nil, *build_multipart_content({
103
+ 'key' => info['path'], 'acl' => info['acl'], 'success_action_status' => 201,
104
+ 'Filename' => info['name'], 'AWSAccessKeyId' => info['accesskeyid'],
105
+ 'Policy' => info['policy'], 'signature' => info['signature'],
106
+ 'Content-Type' => info['mime_type'], 'file' => file
107
+ }))
108
+
109
+ die("S3 is mean to us.") unless res.class == Net::HTTPCreated
110
+
111
+
112
+ # Print the URL to the file to stdout.
113
+ puts "#{info['s3_url']}#{info['path']}"
metadata ADDED
@@ -0,0 +1,64 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: ghup
3
+ version: !ruby/object:Gem::Version
4
+ prerelease: false
5
+ segments:
6
+ - 0
7
+ - 0
8
+ - 1
9
+ version: 0.0.1
10
+ platform: ruby
11
+ authors:
12
+ - Tomas Carnecky
13
+ autorequire:
14
+ bindir: bin
15
+ cert_chain: []
16
+
17
+ date: 2012-05-29 00:00:00 +02:00
18
+ default_executable:
19
+ dependencies: []
20
+
21
+ description:
22
+ email:
23
+ - tomas.carnecky@gmail.com
24
+ executables:
25
+ - ghup
26
+ extensions: []
27
+
28
+ extra_rdoc_files: []
29
+
30
+ files:
31
+ - bin/ghup
32
+ - README.md
33
+ has_rdoc: true
34
+ homepage: https://github.com/wereHamster/ghup
35
+ licenses: []
36
+
37
+ post_install_message:
38
+ rdoc_options: []
39
+
40
+ require_paths:
41
+ - lib
42
+ required_ruby_version: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ segments:
47
+ - 0
48
+ version: "0"
49
+ required_rubygems_version: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - ">="
52
+ - !ruby/object:Gem::Version
53
+ segments:
54
+ - 0
55
+ version: "0"
56
+ requirements: []
57
+
58
+ rubyforge_project:
59
+ rubygems_version: 1.3.6
60
+ signing_key:
61
+ specification_version: 3
62
+ summary: Commandline github upload script
63
+ test_files: []
64
+