fisherman 0.1.0

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.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: df9bf0fb1b8cf3b4671971b6a3e8e25f64d845ce
4
+ data.tar.gz: 0e160ccdbaa9e82773fc338f80c0d17a332caf16
5
+ SHA512:
6
+ metadata.gz: 11cfc89593f018d57c3a989b0095d23aee4ffd7f60ef7cb94a9c71f5721d83c4bddae3644d689bf2edfd1259f12b0dba0e0b5d00e6a8daec1ee43f7f0fe43bb3
7
+ data.tar.gz: 6bceba0ac1aa3f0f0f2230a204e34aa07e494a92b0960f27329e13aa2edf37b2b26a320cd05122a0924016e0175a8ddc1d15ccae18bf59b2f5430a6e7f27f575
@@ -0,0 +1,9 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in fisherman.gemspec
4
+ gemspec
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2017
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,53 @@
1
+ # Fisherman
2
+
3
+ A library that wraps Snapfish's unpublished API used on their site. Currently,
4
+ only a very few calls are supported, but there seems to be a lot more that
5
+ could be implemented. I only needed enough coverage to get all the photo URLs,
6
+ but pull requests are welcome for additional API support.
7
+
8
+ API Usage:
9
+
10
+ ```ruby
11
+ require 'fisherman'
12
+
13
+ # Currently needs an active access token from the site. To get yours, log in,
14
+ # open the developer tools and look for the `access_token` header on one of the
15
+ # API requests.
16
+ access_token = ...
17
+ Snapfish.connect(access_token)
18
+
19
+ # Get all albums -- returns an enumerable collection of Snapfish::Album objects
20
+ albums = Snapfish::AlbumCollection.new.to_a
21
+
22
+ # Print an album's name
23
+ puts albums.first.name
24
+
25
+ # Get all photos from an album
26
+ photos = albums.first.assets
27
+
28
+ # Print a photo's URL
29
+ puts photos.first.hires_url
30
+ ```
31
+
32
+ Included is a script called `extract_snapfish_albums` which returns information
33
+ on all an account's albums, including URLs for downloading high-resolution
34
+ photos. To use it:
35
+
36
+ ```bash
37
+ > TOKEN=<access_token from site>
38
+ > # Output a JSON file describing each ablum
39
+ > extract_snapfish_albums $TOKEN > albums.json
40
+ > # Output a bash script that downloads all album photos
41
+ > BASH_SCRIPT=true extract_snapfish_albums $TOKEN > download.sh
42
+ ```
43
+
44
+ ## Development
45
+
46
+ After checking out the repo, run `bin/setup` to install dependencies. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
47
+
48
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
49
+
50
+ ## Contributing
51
+
52
+ Bug reports and pull requests are welcome on GitHub at https://github.com/rustygeldmacher/fisherman.
53
+
@@ -0,0 +1,2 @@
1
+ require "bundler/gem_tasks"
2
+ task :default => :spec
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "fisherman"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,51 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'fisherman'
4
+ require 'shellwords'
5
+
6
+ # TODO:
7
+ # - Log in using email/password
8
+ # - Use GetOpt for args
9
+
10
+ token = ARGV[0]
11
+ if token.nil?
12
+ puts "** Usage: snapfish_albums <TOKEN>"
13
+ exit 1
14
+ end
15
+
16
+ Snapfish.connect(token)
17
+
18
+ STDERR.puts 'Gathering album information...'
19
+
20
+ albums_json = Snapfish::AlbumCollection.new.map do |album|
21
+ photos_json = album.assets.map(&:as_json)
22
+ album.as_json.merge(photos: photos_json)
23
+ end
24
+
25
+ albums_json.sort_by! { |album| album[:created_at] }
26
+
27
+ if ENV['BASH_SCRIPT']
28
+ puts <<-BASH
29
+ #!/bin/bash
30
+ #
31
+ # Downloads all Snapfish albums and sorts them into folders by album title.
32
+ # Folders are created in the current directory.
33
+ # Requires `wget`.
34
+ #
35
+ BASH
36
+
37
+ albums_json.each_with_index do |album_json, album_index|
38
+ directory_name = [
39
+ album_index.to_s.rjust(4, '0'),
40
+ Shellwords.escape(album_json[:name])
41
+ ].join(' - ')
42
+ puts "mkdir -p \"#{directory_name}\""
43
+ album_json[:photos].each_with_index do |photo_json, photo_index|
44
+ file_name = photo_index.to_s.rjust(4, '0') + '.' + photo_json[:file_extension]
45
+ destination_path = File.join(directory_name, file_name)
46
+ puts "wget \"#{photo_json[:url]}\" -O \"#{destination_path}\""
47
+ end
48
+ end
49
+ else
50
+ puts JSON.pretty_generate(albums_json)
51
+ end
@@ -0,0 +1,29 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'fisherman/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "fisherman"
8
+ spec.version = Fisherman::VERSION
9
+ spec.authors = ["Rusty Geldmacher"]
10
+ spec.email = ["russell.geldmacher@gmail.com"]
11
+
12
+ spec.summary = %q{API wrapper for Snapfish}
13
+ spec.description = %q{API wrapper for Snapfish's unpublished APIs}
14
+ spec.homepage = "https://github.com/rustygeldmacher/fisherman"
15
+
16
+ spec.files = `git ls-files -z`.split("\x0").reject do |f|
17
+ f.match(%r{^(test|spec|features)/})
18
+ end
19
+ spec.bindir = "exe"
20
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
21
+ spec.require_paths = ["lib"]
22
+
23
+ spec.add_development_dependency "bundler", "~> 1.13"
24
+ spec.add_development_dependency "rake", "~> 10.0"
25
+ spec.add_development_dependency "faraday", "~> 0.11.0"
26
+ spec.add_development_dependency "faraday_middleware", "~> 0.11.0"
27
+
28
+ spec.add_development_dependency "pry-byebug"
29
+ end
@@ -0,0 +1,9 @@
1
+ require 'json'
2
+ require 'faraday'
3
+ require 'faraday_middleware'
4
+
5
+ require 'fisherman/version'
6
+ require 'snapfish'
7
+
8
+ module Fisherman
9
+ end
@@ -0,0 +1,3 @@
1
+ module Fisherman
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,21 @@
1
+ require 'snapfish/base'
2
+ require 'snapfish/asset'
3
+ require 'snapfish/album'
4
+ require 'snapfish/album_collection'
5
+
6
+ module Snapfish
7
+ API_BASE_URL = 'https://assets-aus.snapfish.com/pict/v2/collection'
8
+
9
+ def self.connect(token)
10
+ connection = Faraday.new(url: API_BASE_URL) do |conn|
11
+ conn.response :json
12
+ conn.adapter Faraday.default_adapter
13
+ end
14
+
15
+ connection.headers['Authorization'] = token
16
+ connection.headers['access_token'] = token
17
+ connection.headers['Accept'] = 'application/json'
18
+
19
+ Snapfish::Base.connection = connection
20
+ end
21
+ end
@@ -0,0 +1,42 @@
1
+ module Snapfish
2
+ class Album < Base
3
+ def id
4
+ json['id']
5
+ end
6
+
7
+ def asset_count
8
+ json['assetIdList'].size
9
+ end
10
+
11
+ def name
12
+ extract_tag('userTags', 'caption')
13
+ end
14
+
15
+ def assets
16
+ album_json = connection.get(album_url,
17
+ assetType: 'ALL',
18
+ limit: 100,
19
+ skip: 0,
20
+ sortCriteria: 'dateTaken',
21
+ sortOrder: 'ascending'
22
+ ).body
23
+
24
+ album_json['entities'].map do |entity_json|
25
+ Asset.new(entity_json)
26
+ end
27
+ end
28
+
29
+ def as_json
30
+ {
31
+ name: name,
32
+ created_at: created_at
33
+ }
34
+ end
35
+
36
+ private
37
+
38
+ def album_url
39
+ "#{id}/assets"
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,26 @@
1
+ module Snapfish
2
+ class AlbumCollection < Base
3
+ include Enumerable
4
+
5
+ def each
6
+ all.each { |album| yield album }
7
+ end
8
+
9
+ private
10
+
11
+ def all
12
+ albums_json = connection.get('monthIndex',
13
+ skip: 0,
14
+ limit: 100,
15
+ minCollection: 1000,
16
+ sortOrder: 'descending',
17
+ timezoneOffset: -300
18
+ ).body
19
+
20
+ albums_json['entityMap'].keys.flat_map do |entity|
21
+ collections = albums_json['entityMap'][entity]['collectionList']
22
+ collections.map { |collection_json| Album.new(collection_json) }
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,34 @@
1
+ module Snapfish
2
+ class Asset < Base
3
+ def filename
4
+ os_metadata = extract_tag('systemTags', 'OS_METADATA')
5
+ if os_metadata && os_metadata = os_metadata['value']
6
+ os_metadata.match(/os.fn=(\S+)/)[1]
7
+ end
8
+ end
9
+
10
+ def caption
11
+ extract_tag('userTags', 'caption')
12
+ end
13
+
14
+ def file_extension
15
+ File.extname(hires_url).downcase.gsub(/^\./, '')
16
+ end
17
+
18
+ def hires_url
19
+ hires_file = json['files'].find { |f| f['fileType'] == 'HIRES' }
20
+ if hires_file
21
+ hires_file['url']
22
+ end
23
+ end
24
+
25
+ def as_json(options = {})
26
+ {
27
+ filename: filename,
28
+ file_extension: file_extension,
29
+ caption: caption,
30
+ url: hires_url
31
+ }
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,45 @@
1
+ module Snapfish
2
+ class Base
3
+ attr_reader :json
4
+
5
+ def initialize(json = {})
6
+ @json = json
7
+ end
8
+
9
+ def self.connection=(connection)
10
+ @@connection = connection
11
+ end
12
+
13
+ def self.connection
14
+ @@connection
15
+ end
16
+
17
+ def created_at
18
+ create_date = json['createDate']
19
+ if create_date
20
+ Time.at(create_date / 1000, create_date % 1000)
21
+ end
22
+ end
23
+
24
+ def updated_at
25
+ update_date = json['updateDate']
26
+ if update_date
27
+ Time.at(update_date / 1000, update_date % 1000)
28
+ end
29
+ end
30
+
31
+ private
32
+
33
+ def extract_tag(tag_group, tag_name)
34
+ tags = json[tag_group] || []
35
+ tag = tags.find { |t| t['key'] == tag_name }
36
+ if tag
37
+ tag['value']
38
+ end
39
+ end
40
+
41
+ def connection
42
+ Snapfish::Base.connection
43
+ end
44
+ end
45
+ end
metadata ADDED
@@ -0,0 +1,130 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: fisherman
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Rusty Geldmacher
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2017-02-11 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: bundler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '1.13'
20
+ type: :development
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '1.13'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - "~>"
32
+ - !ruby/object:Gem::Version
33
+ version: '10.0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - "~>"
39
+ - !ruby/object:Gem::Version
40
+ version: '10.0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: faraday
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: 0.11.0
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: 0.11.0
55
+ - !ruby/object:Gem::Dependency
56
+ name: faraday_middleware
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: 0.11.0
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: 0.11.0
69
+ - !ruby/object:Gem::Dependency
70
+ name: pry-byebug
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ description: API wrapper for Snapfish's unpublished APIs
84
+ email:
85
+ - russell.geldmacher@gmail.com
86
+ executables:
87
+ - extract_snapfish_albums
88
+ extensions: []
89
+ extra_rdoc_files: []
90
+ files:
91
+ - ".gitignore"
92
+ - Gemfile
93
+ - LICENSE
94
+ - README.md
95
+ - Rakefile
96
+ - bin/console
97
+ - bin/setup
98
+ - exe/extract_snapfish_albums
99
+ - fisherman.gemspec
100
+ - lib/fisherman.rb
101
+ - lib/fisherman/version.rb
102
+ - lib/snapfish.rb
103
+ - lib/snapfish/album.rb
104
+ - lib/snapfish/album_collection.rb
105
+ - lib/snapfish/asset.rb
106
+ - lib/snapfish/base.rb
107
+ homepage: https://github.com/rustygeldmacher/fisherman
108
+ licenses: []
109
+ metadata: {}
110
+ post_install_message:
111
+ rdoc_options: []
112
+ require_paths:
113
+ - lib
114
+ required_ruby_version: !ruby/object:Gem::Requirement
115
+ requirements:
116
+ - - ">="
117
+ - !ruby/object:Gem::Version
118
+ version: '0'
119
+ required_rubygems_version: !ruby/object:Gem::Requirement
120
+ requirements:
121
+ - - ">="
122
+ - !ruby/object:Gem::Version
123
+ version: '0'
124
+ requirements: []
125
+ rubyforge_project:
126
+ rubygems_version: 2.4.5
127
+ signing_key:
128
+ specification_version: 4
129
+ summary: API wrapper for Snapfish
130
+ test_files: []