I've been trying to build a customised to-do app with a possibility to add recurring tasks.
My first approach was to use recurring_select on the front and ice_cube logic in the back. I managed to generate a schedule with all desired occurrences but the problem I encountered is that this way I can no longer mark a recurring task as complete, as it's only its occurrence that's displaying.
Here's some of the code:
*task.rb*
class Task < ApplicationRecord
(...)
serialize :recurrence, Hash
def recurrence=(value)
# byebug
if value != "null" && RecurringSelect.is_valid_rule?(value)
super(RecurringSelect.dirty_hash_to_rule(value).to_hash)
else
super(nil)
end
end
def rule
IceCube::Rule.from_hash recurrence
end
def schedule(start)
schedule = IceCube::Schedule.new(start)
schedule.add_recurrence_rule(rule)
schedule
end
def display_tasks(start)
if recurrence.empty?
[self]
else
start_date = start.beginning_of_week
end_date = start.end_of_week
schedule(start_date).occurrences(end_date).map do |date|
Task.new(id: id, name: name, start_time: date)
end
end
end
end
*tasks_controller.rb*
class TasksController < ApplicationController
before_action :set_task, only: [:complete, :uncomplete, :show]
(...)
def index
(...)
@display_tasks = @tasks.flat_map{ |t| t.display_tasks(params.fetch(:start_date, Time.zone.now).to_date ) }
end
(...)
end
I was wondering if there's maybe a better way to approach it than using the gems? I was reading about scheduling rake tasks but I've never done it myself so I'm not sure if that's the way to go either.
Thanks in advance.
Yes, there is a better way to do recurring tasks using rake tasks and whenever gem. It has an extremely easy to used DSL
All you need to do is define your rake task and then put the schedule configuration inside a schedule.rb.
However, whenever utilizes cron jobs and is not supported by Heroku. If you are using Heroku, then you should use Heroku Scheduler. All you need to do is define your tasks in a tasks/scheduler.rake, install the addon and let Heroku Scheduler do the rest.
This approaches will help keep your models cleaner and remove the scheduling information from them.
To the second part of your question that is marking recurring tasks as complete, all you need to do is set a boolean attribute say completed
to true when the recurring task is marked as complete and then adding a guard clause in your rake tasks like return if task.completed?
to skip processing for that task.