Class: Checkoff::Timelines

Inherits:
Object
  • Object
show all
Extended by:
CacheMethod::ClassMethods
Defined in:
lib/checkoff/timelines.rb

Overview

Manages timelines of dependent tasks with dates and milestones

Constant Summary collapse

MINUTE =
60
HOUR =
MINUTE * 60
DAY =
24 * HOUR
REALLY_LONG_CACHE_TIME =
HOUR * 1
LONG_CACHE_TIME =
MINUTE * 15
SHORT_CACHE_TIME =
MINUTE

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(config: Checkoff::Internal::ConfigLoader.load(:asana), workspaces: Checkoff::Workspaces.new(config: config), sections: Checkoff::Sections.new(config: config), tasks: Checkoff::Tasks.new(config: config), portfolios: Checkoff::Portfolios.new(config: config), clients: Checkoff::Clients.new(config: config), client: clients.client) ⇒ Timelines

Returns a new instance of Timelines.

Parameters:

  • config (Hash) (defaults to: Checkoff::Internal::ConfigLoader.load(:asana))
  • workspaces (Checkoff::Workspaces) (defaults to: Checkoff::Workspaces.new(config: config))
  • sections (Checkoff::Sections) (defaults to: Checkoff::Sections.new(config: config))
  • tasks (Checkoff::Tasks) (defaults to: Checkoff::Tasks.new(config: config))
  • portfolios (Checkoff::Portfolios) (defaults to: Checkoff::Portfolios.new(config: config))
  • clients (Checkoff::Clients) (defaults to: Checkoff::Clients.new(config: config))
  • client (Asana::Client) (defaults to: clients.client)


33
34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/checkoff/timelines.rb', line 33

def initialize(config: Checkoff::Internal::ConfigLoader.load(:asana),
               workspaces: Checkoff::Workspaces.new(config: config),
               sections: Checkoff::Sections.new(config: config),
               tasks: Checkoff::Tasks.new(config: config),
               portfolios: Checkoff::Portfolios.new(config: config),
               clients: Checkoff::Clients.new(config: config),
               client: clients.client)
  @workspaces = workspaces
  @sections = sections
  @tasks = tasks
  @portfolios = portfolios
  @client = client
end

Class Method Details

.runvoid

This method returns an undefined value.



167
168
169
170
171
172
173
174
175
176
177
# File 'lib/checkoff/timelines.rb', line 167

def run
  # @sg-ignore
  # @type [String]
  # workspace_name = ARGV[0] || raise('Please pass workspace name as first argument')
  # @sg-ignore
  # @type [String]
  # timeline_name = ARGV[1] || raise('Please pass timeline name as second argument')
  # timelines = Checkoff::Timelines.new
  # timeline = timelines.timeline_or_raise(workspace_name, timeline_name)
  # puts "Results: #{timeline}"
end

Instance Method Details

#any_milestone_depends_on_this_task?(task, limit_to_portfolio_name: nil) ⇒ Boolean

Parameters:

  • task (Asana::Resources::Task)
  • limit_to_portfolio_name (String, nil) (defaults to: nil)

Returns:

  • (Boolean)


97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
# File 'lib/checkoff/timelines.rb', line 97

def any_milestone_depends_on_this_task?(task, limit_to_portfolio_name: nil)
  unless limit_to_portfolio_name.nil?
    limit_to_projects = @portfolios.projects_in_portfolio(@workspaces.default_workspace.name,
                                                          limit_to_portfolio_name)
  end

  all_dependent_milestones = nil
  task.memberships.all? do |membership_data|
    unless limit_to_portfolio_name.nil?
      project_gid = membership_data.fetch('project').fetch('gid')
      next true unless limit_to_projects.map(&:gid).include? project_gid
    end

    all_dependent_milestones ||=
      @tasks.all_dependent_tasks(task,
                                 extra_task_fields: ['resource_subtype',
                                                     'memberships.project.gid']).select do |dependent_task|
        dependent_task.resource_subtype == 'milestone'
      end

    all_dependent_milestones.any? do |milestone|
      milestone.memberships.any? do |milestone_membership_data|
        milestone_membership_data.fetch('project').fetch('gid') == project_gid
      end
    end
  end
end

#last_milestone_in_section(section_gid) ⇒ Asana::Resources::Task?

Parameters:

  • section_gid (String)

Returns:

  • (Asana::Resources::Task, nil)


128
129
130
131
132
133
134
# File 'lib/checkoff/timelines.rb', line 128

def last_milestone_in_section(section_gid)
  # @type [Array<Asana::Resources::Task>]
  task_list = @sections.tasks_by_section_gid(section_gid,
                                             extra_fields: ['resource_subtype']).to_a
  last_task = task_list.last
  last_task&.resource_subtype == 'milestone' ? last_task : nil
end

#last_task_milestone_depends_on_this_task?(task, limit_to_portfolio_name: nil) ⇒ Boolean

Parameters:

  • task (Asana::Resources::Task)
  • limit_to_portfolio_name (String, nil) (defaults to: nil)

Returns:

  • (Boolean)


66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
# File 'lib/checkoff/timelines.rb', line 66

def last_task_milestone_depends_on_this_task?(task, limit_to_portfolio_name: nil)
  unless limit_to_portfolio_name.nil?
    limit_to_projects = @portfolios.projects_in_portfolio(@workspaces.default_workspace.name,
                                                          limit_to_portfolio_name)
  end

  all_dependent_task_gids = nil
  task.memberships.all? do |membership_data|
    unless limit_to_portfolio_name.nil?
      project_gid = membership_data.fetch('project').fetch('gid')
      next true unless limit_to_projects.map(&:gid).include? project_gid
    end
    # @type [Hash{String => String}]
    section_data = membership_data.fetch('section')
    # @type [String]
    section_gid = section_data.fetch('gid')

    last_milestone = last_milestone_in_section(section_gid)

    next false if last_milestone.nil?

    next true if last_milestone.gid == task.gid

    all_dependent_task_gids ||= @tasks.all_dependent_tasks(task).map(&:gid)

    all_dependent_task_gids.include? last_milestone.gid
  end
end

#task_dependent_on_previous_section_last_milestone?(task, limit_to_portfolio_gid: nil) ⇒ Boolean

Parameters:

  • task (Asana::Resources::Task)
  • limit_to_portfolio_gid (String, nil) (defaults to: nil)
  • project_name (String)

Returns:

  • (Boolean)


50
51
52
53
54
55
56
57
58
59
60
61
62
# File 'lib/checkoff/timelines.rb', line 50

def task_dependent_on_previous_section_last_milestone?(task, limit_to_portfolio_gid: nil)
  task_data = @tasks.task_to_h(task)
  # @sg-ignore
  # @type [Array<Hash{String => Hash{String => String}}>]
  memberships_data = task_data.fetch('memberships')
  memberships_data.all? do |membership_data|
    # @type [Hash{String => String}]
    section_data = membership_data.fetch('section')
    section_gid = section_data.fetch('gid')
    section = @sections.section_by_gid(section_gid)
    task_data_dependent_on_previous_section_last_milestone?(task_data, section)
  end
end