checkoff 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: ac558deb21242fbafa8896765220574a9b7386ff
4
+ data.tar.gz: efe68230c0e4d485942c3bca5a7a21b94cb0acfa
5
+ SHA512:
6
+ metadata.gz: 7e67efc0190d8c58993e0657d3681da8266e274f246d7a15f13be90de50f12ead8c90d871289a5265e7e055e67107dfa8a8bdee44bd176f143ec444a97a2d132
7
+ data.tar.gz: 7dcffa12ba7ecf02b32d5cf48443214c5e265f76e7eed9324ce49effadbb21c904f25c8ebf3960ad3d1cbc08e80bcf6197727c4a409e75bc4aa229ec46459a39
data/.gitignore ADDED
@@ -0,0 +1,12 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+ /coverage/.resultset.json
10
+ /coverage/assets/
11
+ /coverage/index.html
12
+ /pkg
data/.rubocop.yml ADDED
@@ -0,0 +1,36 @@
1
+ # I like trailing commas in maps. They let me insert new elements and
2
+ # see them as one line in a diff, not two.
3
+ Style/TrailingCommaInLiteral:
4
+ EnforcedStyleForMultiline: comma
5
+
6
+ # I use keyword arguments for a poor man's dependency injection to cut
7
+ # down on the magic in my tests.
8
+ ParameterLists:
9
+ CountKeywordArgs: false
10
+
11
+ # If i'm using one function name and returning the contents of an
12
+ # attribute, that's OK. The alternative would be this, which I find
13
+ # confusing and often not really what I mean:
14
+ #
15
+ # attr_reader :something_else
16
+ # alias_method :something, :something_else
17
+ TrivialAccessors:
18
+ ExactNameMatch: true
19
+
20
+ #
21
+ # Add 'XXX' to the standard list
22
+ #
23
+ Style/CommentAnnotation:
24
+ Keywords:
25
+ - "TOD\
26
+ O"
27
+ - "FIXM\
28
+ E"
29
+ - "OPTIMIZ\
30
+ E"
31
+ - "HAC\
32
+ K"
33
+ - "REVIE\
34
+ W"
35
+ - "XX\
36
+ X"
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ ruby-2.1.0
data/.travis.yml ADDED
@@ -0,0 +1,11 @@
1
+ before_install:
2
+ - gem install bundler
3
+ language: ruby
4
+ rvm:
5
+ - ruby-2.1
6
+ - ruby-2.2
7
+ - ruby-2.3.1
8
+ # - jruby-head # see https://github.com/apiology/quality/issues/59
9
+ # - jruby-9.0 # see https://github.com/apiology/quality/issues/59
10
+ # - ruby-head # Upstream bug - see https://travis-ci.org/apiology/checkoff/jobs/138626934
11
+
@@ -0,0 +1,49 @@
1
+ # Contributor Code of Conduct
2
+
3
+ As contributors and maintainers of this project, and in the interest of
4
+ fostering an open and welcoming community, we pledge to respect all people who
5
+ contribute through reporting issues, posting feature requests, updating
6
+ documentation, submitting pull requests or patches, and other activities.
7
+
8
+ We are committed to making participation in this project a harassment-free
9
+ experience for everyone, regardless of level of experience, gender, gender
10
+ identity and expression, sexual orientation, disability, personal appearance,
11
+ body size, race, ethnicity, age, religion, or nationality.
12
+
13
+ Examples of unacceptable behavior by participants include:
14
+
15
+ * The use of sexualized language or imagery
16
+ * Personal attacks
17
+ * Trolling or insulting/derogatory comments
18
+ * Public or private harassment
19
+ * Publishing other's private information, such as physical or electronic
20
+ addresses, without explicit permission
21
+ * Other unethical or unprofessional conduct
22
+
23
+ Project maintainers have the right and responsibility to remove, edit, or
24
+ reject comments, commits, code, wiki edits, issues, and other contributions
25
+ that are not aligned to this Code of Conduct, or to ban temporarily or
26
+ permanently any contributor for other behaviors that they deem inappropriate,
27
+ threatening, offensive, or harmful.
28
+
29
+ By adopting this Code of Conduct, project maintainers commit themselves to
30
+ fairly and consistently applying these principles to every aspect of managing
31
+ this project. Project maintainers who do not follow or enforce the Code of
32
+ Conduct may be permanently removed from the project team.
33
+
34
+ This code of conduct applies both within project spaces and in public spaces
35
+ when an individual is representing the project or its community.
36
+
37
+ Instances of abusive, harassing, or otherwise unacceptable behavior may be
38
+ reported by contacting a project maintainer at vince@broz.cc. All
39
+ complaints will be reviewed and investigated and will result in a response that
40
+ is deemed necessary and appropriate to the circumstances. Maintainers are
41
+ obligated to maintain confidentiality with regard to the reporter of an
42
+ incident.
43
+
44
+ This Code of Conduct is adapted from the [Contributor Covenant][homepage],
45
+ version 1.3.0, available at
46
+ [http://contributor-covenant.org/version/1/3/0/][version]
47
+
48
+ [homepage]: http://contributor-covenant.org
49
+ [version]: http://contributor-covenant.org/version/1/3/0/
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in checkoff.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2016 Vince Broz
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
13
+ all 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
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,38 @@
1
+ Command-line and gem client for Asana (unofficial)
2
+
3
+ [![Circle CI](https://circleci.com/gh/apiology/checkoff.svg?style=svg)](https://circleci.com/gh/apiology/checkoff)
4
+ [![Travis CI](https://travis-ci.org/apiology/checkoff.svg?branch=master)](https://travis-ci.org/apiology/checkoff)
5
+
6
+ ## Caching
7
+
8
+ Note that I don't know of a way through the Asana API to target
9
+ individual sections and pull back only those tasks, which is a real
10
+ bummer! As a result, sometimes the number of tasks brought back to
11
+ answer a query is really large and takes a while. To help make that
12
+ less annoying, I do caching using memcached; you'll need to install
13
+ it.
14
+
15
+ ## Installing
16
+
17
+ ```bash
18
+ brew install memcached
19
+ gem install checkoff
20
+
21
+ ```
22
+
23
+ ## Using
24
+
25
+ ```bash
26
+ $ checkoff --help
27
+ View tasks:
28
+ exe/checkoff view workspace project [section]
29
+
30
+ 'project' can be set to a project name, or :my_tasks, :my_tasks_upcoming, :my_tasks_new, or :my_tasks_today
31
+ ```
32
+
33
+ ## Developing
34
+
35
+ ```bash
36
+ bundle install
37
+ bundle exec exe/checkoff --help
38
+ ```
data/Rakefile ADDED
@@ -0,0 +1,6 @@
1
+ require 'bundler/gem_tasks'
2
+
3
+ Dir['lib/tasks/**/*.rake'].each { |t| load t }
4
+
5
+ desc 'Default: Run specs and check quality.'
6
+ task default: [:localtest]
data/bin/checkoff ADDED
@@ -0,0 +1 @@
1
+ #!/usr/bin/env ruby
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "checkoff"
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
data/bin/setup ADDED
@@ -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
data/checkoff.gemspec ADDED
@@ -0,0 +1,34 @@
1
+ # coding: ascii
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'checkoff/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = 'checkoff'
8
+ spec.version = Checkoff::VERSION
9
+ spec.authors = ['Vince Broz']
10
+ spec.email = ['vince@broz.cc']
11
+
12
+ spec.summary = 'Command-line and gem client for Asana (unofficial)'
13
+ spec.homepage = 'http://github.com/apiology/checkoff'
14
+ spec.license = 'MIT'
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_runtime_dependency 'dalli'
24
+ spec.add_runtime_dependency 'cache_method'
25
+ spec.add_runtime_dependency 'asana'
26
+
27
+ spec.add_development_dependency 'bundler', '~> 1.12'
28
+ spec.add_development_dependency 'rake', '~> 10.0'
29
+ spec.add_development_dependency 'rspec', '>=3.4'
30
+ spec.add_development_dependency 'quality'
31
+ spec.add_development_dependency 'simplecov'
32
+ spec.add_development_dependency 'minitest-profile'
33
+ spec.add_development_dependency 'mocha'
34
+ end
data/circle.yml ADDED
@@ -0,0 +1,6 @@
1
+ test:
2
+ override:
3
+ - bundle exec rake localtest
4
+ general:
5
+ artifacts:
6
+ - "coverage"
@@ -0,0 +1,5 @@
1
+ {
2
+ "result": {
3
+ "covered_percent": 98.31
4
+ }
5
+ }
data/exe/checkoff ADDED
@@ -0,0 +1,7 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'checkoff/cli'
4
+
5
+ CacheMethod.config.storage = Dalli::Client.new('memcached:11211')
6
+ cli = Checkoff::CLI.new
7
+ puts cli.run(ARGV)
@@ -0,0 +1,79 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'ostruct'
4
+ require 'dalli'
5
+ require 'cache_method'
6
+ require_relative 'projects'
7
+ require_relative 'tasks'
8
+ require_relative 'sections'
9
+
10
+ module Checkoff
11
+ # Provide ability for CLI to pull Asana items
12
+ class CLI
13
+ attr_reader :sections, :stderr
14
+
15
+ def initialize(sections: Checkoff::Sections.new,
16
+ stderr: STDERR,
17
+ kernel: Kernel)
18
+ @sections = sections
19
+ @kernel = kernel
20
+ @stderr = stderr
21
+ end
22
+
23
+ def task_to_hash(task)
24
+ {
25
+ name: task.name,
26
+ }
27
+ end
28
+
29
+ def tasks_to_hash(tasks)
30
+ tasks.map { |task| task_to_hash(task) }
31
+ end
32
+
33
+ def run_on_project(workspace, project)
34
+ tasks_by_section =
35
+ sections.tasks_by_section(workspace, project)
36
+ tasks_by_section.update(tasks_by_section) do |_key, tasks|
37
+ tasks_to_hash(tasks)
38
+ end
39
+ tasks_by_section.to_json
40
+ end
41
+
42
+ def run_on_section(workspace, project, section)
43
+ section = nil if section == ''
44
+ tasks = sections.tasks(workspace, project, section) || []
45
+ tasks_to_hash(tasks).to_json
46
+ end
47
+
48
+ def validate_args!(args)
49
+ mode, _workspace, project, _section = args
50
+ return unless project.nil? || mode != 'view'
51
+
52
+ output_help
53
+ exit(1)
54
+ end
55
+
56
+ def parse_args(args)
57
+ validate_args!(args)
58
+ args[1..-1]
59
+ end
60
+
61
+ def output_help
62
+ stderr.puts 'View tasks:'
63
+ stderr.puts " #{$PROGRAM_NAME} view workspace project [section]"
64
+ stderr.puts
65
+ stderr.puts "'project' can be set to a project name, or :my_tasks, " \
66
+ ':my_tasks_upcoming, :my_tasks_new, or :my_tasks_today'
67
+ end
68
+
69
+ def run(args)
70
+ workspace, project, section = parse_args(args)
71
+ project = project[1..-1].to_sym if project.start_with? ':'
72
+ if section.nil?
73
+ run_on_project(workspace, project)
74
+ else
75
+ run_on_section(workspace, project, section)
76
+ end
77
+ end
78
+ end
79
+ end
@@ -0,0 +1,11 @@
1
+ require 'yaml'
2
+ require 'active_support/core_ext/hash'
3
+
4
+ # Load configuration file
5
+ class ConfigLoader
6
+ def self.load(sym)
7
+ file = "#{sym}.yml"
8
+ YAML.load_file(File.expand_path("~/private/#{file}"))
9
+ .with_indifferent_access
10
+ end
11
+ end
@@ -0,0 +1,93 @@
1
+ require_relative 'config_loader'
2
+
3
+ require 'cache_method'
4
+ require 'asana'
5
+
6
+ # Pull tasks from asana.com
7
+ #
8
+ # Convention:
9
+ # _raw: Returns tasks objects, including section-tasks
10
+ # _tasks: Returns task objects
11
+ # _task_names: Returns an array of strings, no sections included
12
+ # _by_section: Returns a hash from section name to array
13
+ module Checkoff
14
+ # Work with projects in Asana
15
+ class Projects
16
+ MINUTE = 60
17
+ HOUR = MINUTE * 60
18
+ DAY = 24 * HOUR
19
+ REALLY_LONG_CACHE_TIME = HOUR * 1
20
+ LONG_CACHE_TIME = MINUTE * 15
21
+ SHORT_CACHE_TIME = MINUTE * 5
22
+
23
+ # XXX: Move low-level functions private
24
+
25
+ def initialize(config: ConfigLoader.load(:asana),
26
+ asana_client: Asana::Client)
27
+ @config = config
28
+ @asana_client = asana_client
29
+ end
30
+
31
+ def client
32
+ @client ||= @asana_client.new do |c|
33
+ c.authentication :access_token, @config[:personal_access_token]
34
+ end
35
+ end
36
+
37
+ def projects
38
+ client.projects
39
+ end
40
+ cache_method :projects, LONG_CACHE_TIME
41
+
42
+ def workspace_by_name(workspace_name)
43
+ client.workspaces.find_all.find do |workspace|
44
+ workspace.name == workspace_name
45
+ end || raise("Could not find workspace #{workspace_name}")
46
+ end
47
+
48
+ def projects_by_workspace_name(workspace_name)
49
+ workspace = workspace_by_name(workspace_name)
50
+ raise "Could not find workspace named #{workspace_name}" unless workspace
51
+ projects.find_by_workspace(workspace: workspace.id)
52
+ end
53
+
54
+ def my_tasks(workspace_name)
55
+ my_tasks = @config[:my_tasks]
56
+ id = @config[:my_tasks][workspace_name] unless my_tasks.nil?
57
+ if my_tasks.nil? || id.nil?
58
+ raise "Please define [:my_tasks][#{workspace_name}] in config file"
59
+ end
60
+ projects.find_by_id(id)
61
+ end
62
+
63
+ def project(workspace_name, project_name)
64
+ if project_name.is_a?(Symbol) && project_name.to_s.start_with?('my_tasks')
65
+ my_tasks(workspace_name)
66
+ else
67
+ STDERR.puts "Looking for #{project_name} under #{workspace_name}"
68
+ projects = projects_by_workspace_name(workspace_name)
69
+ projects.find do |project|
70
+ project.name == project_name
71
+ end
72
+ end
73
+ end
74
+ cache_method :project, LONG_CACHE_TIME
75
+
76
+ def active_tasks(tasks)
77
+ tasks.select { |task| task.completed_at.nil? }
78
+ end
79
+
80
+ def task_options
81
+ {
82
+ options: {
83
+ fields: %w(name assignee_status completed_at due_at due_on),
84
+ },
85
+ }
86
+ end
87
+
88
+ def tasks_from_project(project)
89
+ project.tasks(task_options).to_a
90
+ end
91
+ cache_method :tasks_from_project, LONG_CACHE_TIME
92
+ end
93
+ end
@@ -0,0 +1,124 @@
1
+ module Checkoff
2
+ # Query different sections of Asana projects
3
+ class Sections
4
+ MINUTE = 60
5
+ LONG_CACHE_TIME = MINUTE * 15
6
+ SHORT_CACHE_TIME = MINUTE * 5
7
+
8
+ attr_reader :projects, :time
9
+
10
+ def initialize(projects: Checkoff::Projects.new,
11
+ time: Time)
12
+ @projects = projects
13
+ @time = time
14
+ end
15
+
16
+ def file_task_by_section(current_section, by_section, task)
17
+ if task.name =~ /:$/
18
+ current_section = task.name
19
+ by_section[current_section] = []
20
+ else
21
+ by_section[current_section] ||= []
22
+ by_section[current_section] << task
23
+ end
24
+ [current_section, by_section]
25
+ end
26
+
27
+ def by_section(tasks)
28
+ current_section = nil
29
+ by_section = {}
30
+ tasks.each do |task|
31
+ current_section, by_section = file_task_by_section(current_section,
32
+ by_section, task)
33
+ end
34
+ by_section
35
+ end
36
+ cache_method :by_section, LONG_CACHE_TIME
37
+
38
+ def tasks_by_section_for_project(project)
39
+ raw_tasks = projects.tasks_from_project(project)
40
+ active_tasks = projects.active_tasks(raw_tasks)
41
+ by_section(active_tasks)
42
+ end
43
+
44
+ def tasks_by_section_for_project_and_assignee_status(project,
45
+ assignee_status)
46
+ raw_tasks = projects.tasks_from_project(project)
47
+ by_assignee_status =
48
+ projects.active_tasks(raw_tasks)
49
+ .group_by(&:assignee_status)
50
+ active_tasks = by_assignee_status[assignee_status]
51
+ by_section(active_tasks)
52
+ end
53
+
54
+ def project_or_raise(workspace_name, project_name)
55
+ project = projects.project(workspace_name, project_name)
56
+ if project.nil?
57
+ raise "Could not find project #{project_name} " \
58
+ "under workspace #{workspace_name}"
59
+ end
60
+ project
61
+ end
62
+
63
+ def tasks_by_section(workspace_name, project_name)
64
+ project = project_or_raise(workspace_name, project_name)
65
+ if project_name == :my_tasks_new
66
+ tasks_by_section_for_project_and_assignee_status(project, 'inbox')
67
+ elsif project_name == :my_tasks_today
68
+ tasks_by_section_for_project_and_assignee_status(project, 'today')
69
+ elsif project_name == :my_tasks_upcoming
70
+ tasks_by_section_for_project_and_assignee_status(project, 'upcoming')
71
+ else
72
+ tasks_by_section_for_project(project)
73
+ end
74
+ end
75
+ cache_method :tasks_by_section, SHORT_CACHE_TIME
76
+
77
+ # XXX: Rename to section_tasks
78
+ def tasks(workspace_name, project_name, section_name)
79
+ tasks_by_section(workspace_name, project_name)[section_name]
80
+ end
81
+ cache_method :tasks, SHORT_CACHE_TIME
82
+
83
+ def section_task_names(workspace_name, project_name, section_name)
84
+ tasks = tasks(workspace_name, project_name, section_name)
85
+ if tasks.nil?
86
+ by_section = tasks_by_section(workspace_name, project_name)
87
+ desc = "#{workspace_name} | #{project_name} | #{section_name}"
88
+ raise "Could not find task names for #{desc}. " \
89
+ "Valid sections: #{by_section.keys}"
90
+ end
91
+ tasks.map(&:name)
92
+ end
93
+ cache_method :section_task_names, SHORT_CACHE_TIME
94
+
95
+ # Returns all subtasks, including section headers
96
+ def raw_subtasks(task)
97
+ task.subtasks(projects.task_options)
98
+ end
99
+ cache_method :raw_subtasks, LONG_CACHE_TIME
100
+
101
+ def task_due?(task)
102
+ if task.due_at
103
+ Time.parse(task.due_at) <= time.now
104
+ elsif task.due_on
105
+ Date.parse(task.due_on) <= time.today
106
+ else
107
+ true # set a due date if you don't want to do this now
108
+ end
109
+ end
110
+
111
+ def project_task_names(workspace_name, project_name)
112
+ by_section = tasks_by_section(workspace_name, project_name)
113
+ by_section.flat_map do |section_name, tasks|
114
+ task_names = tasks.map(&:name)
115
+ if section_name.nil?
116
+ task_names
117
+ else
118
+ [section_name, task_names]
119
+ end
120
+ end
121
+ end
122
+ cache_method :project_task_names, SHORT_CACHE_TIME
123
+ end
124
+ end
@@ -0,0 +1,23 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require_relative 'sections'
4
+
5
+ module Checkoff
6
+ # Pull things from 'my tasks' in Asana
7
+ class Tasks
8
+ MINUTE = 60
9
+ HOUR = MINUTE * 60
10
+ DAY = 24 * HOUR
11
+ REALLY_LONG_CACHE_TIME = HOUR
12
+ LONG_CACHE_TIME = MINUTE * 15
13
+ SHORT_CACHE_TIME = MINUTE * 5
14
+
15
+ def initialize
16
+ @sections = Checkoff::Sections.new
17
+ end
18
+
19
+ def tasks_minus_sections(tasks)
20
+ @sections.by_section(tasks).values.flatten
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,3 @@
1
+ module Checkoff
2
+ VERSION = '0.1.0'.freeze
3
+ end
data/lib/checkoff.rb ADDED
@@ -0,0 +1,4 @@
1
+ require 'checkoff/version'
2
+ require 'checkoff/projects'
3
+ require 'checkoff/sections'
4
+ require 'checkoff/tasks'
data/lib/tasks/ci.rake ADDED
@@ -0,0 +1 @@
1
+ task ci: :localtest
@@ -0,0 +1,5 @@
1
+ task :clear_metrics do |_t|
2
+ ret =
3
+ system('git checkout coverage/.last_run.json metrics/*_high_water_mark')
4
+ raise unless ret
5
+ end
@@ -0,0 +1 @@
1
+ task default: :localtest
@@ -0,0 +1,7 @@
1
+ require 'rspec/core/rake_task'
2
+
3
+ desc 'Run features'
4
+ RSpec::Core::RakeTask.new(:feature) do |task|
5
+ task.pattern = 'feature/**/*_spec.rb'
6
+ task.rspec_opts = '--format doc'
7
+ end
@@ -0,0 +1 @@
1
+ task localtest: [:clear_metrics, :test, :quality]
@@ -0,0 +1,6 @@
1
+ require 'quality/rake/task'
2
+
3
+ Quality::Rake::Task.new do |task|
4
+ task.skip_tools = ['reek']
5
+ task.output_dir = 'metrics'
6
+ end
@@ -0,0 +1,7 @@
1
+ require 'rspec/core/rake_task'
2
+
3
+ desc 'Run specs'
4
+ RSpec::Core::RakeTask.new(:spec) do |task|
5
+ task.pattern = 'spec/**/*_spec.rb'
6
+ task.rspec_opts = '--format doc'
7
+ end
@@ -0,0 +1,8 @@
1
+ require 'rake/testtask'
2
+
3
+ Rake::TestTask.new do |t|
4
+ t.libs << 'test/unit'
5
+ t.libs << 'lib/checkoff'
6
+ t.test_files = FileList['test/unit/**/test*.rb']
7
+ # t.verbose = true
8
+ end
@@ -0,0 +1 @@
1
+ 484
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1 @@
1
+ 0
@@ -0,0 +1,2 @@
1
+ 11
2
+
@@ -0,0 +1 @@
1
+ 2
metadata ADDED
@@ -0,0 +1,227 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: checkoff
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Vince Broz
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2016-06-18 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: dalli
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: cache_method
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: asana
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: bundler
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - "~>"
60
+ - !ruby/object:Gem::Version
61
+ version: '1.12'
62
+ type: :development
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - "~>"
67
+ - !ruby/object:Gem::Version
68
+ version: '1.12'
69
+ - !ruby/object:Gem::Dependency
70
+ name: rake
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - "~>"
74
+ - !ruby/object:Gem::Version
75
+ version: '10.0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - "~>"
81
+ - !ruby/object:Gem::Version
82
+ version: '10.0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: rspec
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '3.4'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '3.4'
97
+ - !ruby/object:Gem::Dependency
98
+ name: quality
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: simplecov
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
125
+ - !ruby/object:Gem::Dependency
126
+ name: minitest-profile
127
+ requirement: !ruby/object:Gem::Requirement
128
+ requirements:
129
+ - - ">="
130
+ - !ruby/object:Gem::Version
131
+ version: '0'
132
+ type: :development
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - ">="
137
+ - !ruby/object:Gem::Version
138
+ version: '0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: mocha
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - ">="
144
+ - !ruby/object:Gem::Version
145
+ version: '0'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - ">="
151
+ - !ruby/object:Gem::Version
152
+ version: '0'
153
+ description:
154
+ email:
155
+ - vince@broz.cc
156
+ executables:
157
+ - checkoff
158
+ extensions: []
159
+ extra_rdoc_files: []
160
+ files:
161
+ - ".gitignore"
162
+ - ".rubocop.yml"
163
+ - ".ruby-version"
164
+ - ".travis.yml"
165
+ - CODE_OF_CONDUCT.md
166
+ - Gemfile
167
+ - LICENSE.txt
168
+ - README.md
169
+ - Rakefile
170
+ - bin/checkoff
171
+ - bin/console
172
+ - bin/setup
173
+ - checkoff.gemspec
174
+ - circle.yml
175
+ - coverage/.last_run.json
176
+ - exe/checkoff
177
+ - lib/checkoff.rb
178
+ - lib/checkoff/cli.rb
179
+ - lib/checkoff/config_loader.rb
180
+ - lib/checkoff/projects.rb
181
+ - lib/checkoff/sections.rb
182
+ - lib/checkoff/tasks.rb
183
+ - lib/checkoff/version.rb
184
+ - lib/tasks/ci.rake
185
+ - lib/tasks/clear_metrics.rake
186
+ - lib/tasks/default.rake
187
+ - lib/tasks/feature.rake
188
+ - lib/tasks/localtest.rake
189
+ - lib/tasks/quality.rake
190
+ - lib/tasks/spec.rake
191
+ - lib/tasks/test.rake
192
+ - metrics/bigfiles_high_water_mark
193
+ - metrics/brakeman_high_water_mark
194
+ - metrics/cane_high_water_mark
195
+ - metrics/eslint_high_water_mark
196
+ - metrics/flay_high_water_mark
197
+ - metrics/flog_high_water_mark
198
+ - metrics/jscs_high_water_mark
199
+ - metrics/pep8_high_water_mark
200
+ - metrics/punchlist_high_water_mark
201
+ - metrics/rails_best_practices_high_water_mark
202
+ - metrics/rubocop_high_water_mark
203
+ homepage: http://github.com/apiology/checkoff
204
+ licenses:
205
+ - MIT
206
+ metadata: {}
207
+ post_install_message:
208
+ rdoc_options: []
209
+ require_paths:
210
+ - lib
211
+ required_ruby_version: !ruby/object:Gem::Requirement
212
+ requirements:
213
+ - - ">="
214
+ - !ruby/object:Gem::Version
215
+ version: '0'
216
+ required_rubygems_version: !ruby/object:Gem::Requirement
217
+ requirements:
218
+ - - ">="
219
+ - !ruby/object:Gem::Version
220
+ version: '0'
221
+ requirements: []
222
+ rubyforge_project:
223
+ rubygems_version: 2.4.6
224
+ signing_key:
225
+ specification_version: 4
226
+ summary: Command-line and gem client for Asana (unofficial)
227
+ test_files: []