Example #1
0
 def on_activate_task(self, uuid):
     if uuid is None:
         util.log("Activate new task dialog")
         New.show_task(self.database)
     else:
         util.log("Activate task {0}", uuid)
         task = self.database.get_task_info(uuid)
         Properties.show_task(self.database, task)
Example #2
0
    def setup_indicator(self):
        if UbuntuIndicator.is_available():
            util.log("AppIndicator is available, using it.")
            self.indicator = UbuntuIndicator()
        else:
            util.log("AppIndicator is not available, using Gtk status icon.")
            self.indicator = GtkIndicator()

        self.indicator.on_add_task = self.on_add_task
        self.indicator.on_toggle = self.on_toggle_search
        self.indicator.on_stop_all = self.on_stop_all
        self.indicator.on_quit = self.on_quit
        self.indicator.on_pull = self.on_pull
        self.indicator.on_task_selected = self.on_task_selected
Example #3
0
    def show_existing_task(self, task):
        util.log("Showing task {0} ...", task.id())

        self.uuid.set_text(str(task.id()))
        self.description.set_text(task.get_summary())
        self.project.set_text(task["project"] or "")
        self.priority.set_text(str(task["priority"]))
        self.notes.set_text(task.get_description() or "")

        self.completed.set_active(task["status"] == "completed")

        if "start" in task:
            self.start.set_label("Stop")
        else:
            self.start.set_label("Start")
Example #4
0
    def add_task(self, properties):
        command = ["task", "add"]

        for k, v in properties.items():
            if k == "summary":
                command.append(v)
            elif k in ("project", "priority"):
                command.append("%s:%s" % (k, v))

        output = util.run_command(command)

        for _taskno in re.findall("Created task (\d+)", output):
            uuid = util.run_command(["task", _taskno, "uuid"]).strip()
            util.log("New task uuid: {0}", uuid)
            save_note(uuid, properties.get("description", ""))
            return uuid
Example #5
0
    def is_available(cls):
        if not HAVE_APPINDICATOR:
            util.log("No appindicator package.")
            return False  # not installed

        user = os.getenv("USER")

        p = subprocess.Popen(["pgrep", "-u", user, "indicator-applet"],
            stdout=subprocess.PIPE)
        out = p.communicate()[0]

        if out.strip() == "":
            util.log("User %s has no indicator-applet running." % user)
            return False  # not running

        return True
Example #6
0
    def on_timer(self):
        """Timer handler which updates the list of tasks and the status."""
        gtk.timeout_add(FREQUENCY * 1000, self.on_timer)

        if self.database.modified_since(self.database_ts):
            util.log("Task database changed.")
            self.database.refresh()
            self.search_dialog.refresh()
            self.menu_add_tasks()
            self.database_ts = int(time.time())

            self.started_at = []
            for task in self.database.get_tasks():
                if task.is_active() and not task.is_closed():
                    self.started_at.append(task.get_start_ts())

        self.update_status()
Example #7
0
    def _on_row_changed(self, view):
        selection = view.get_selection()
        selection.set_mode(gtk.SELECTION_SINGLE)
        tree_model, tree_iter = selection.get_selected()

        if not tree_iter:
            self.selected_task_id = None
            self.selected_task = None

        else:
            self.selected_task_id = tree_model.get_value(tree_iter, 0)
            util.log("Selected task {0}", self.selected_task_id)

            self.selected_task = None
            for task in self.all_tasks:
                if str(task.id()) == self.selected_task_id:
                    self.selected_task = task

                    self.pmenu_edit.show()

                    if task.is_closed():
                        self.pmenu_start.hide()
                        self.pmenu_stop.hide()
                        self.pmenu_done.hide()
                        self.pmenu_restart.show()
                        self.pmenu_links.show()

                    elif task.is_active():
                        self.pmenu_start.hide()
                        self.pmenu_stop.show()
                        self.pmenu_done.show()
                        self.pmenu_restart.hide()
                        self.pmenu_links.show()

                    else:  # pending
                        self.pmenu_start.show()
                        self.pmenu_stop.hide()
                        self.pmenu_done.show()
                        self.pmenu_restart.hide()
                        self.pmenu_links.show()

                    if "://" not in task.get_summary():
                        self.pmenu_links.hide()
Example #8
0
def show_existing_instance():
    """
    Open up the previous instance, if there is one.

    FIXME: use dbus.
    """
    p = subprocess.Popen(["pgrep", "-f", "/task-indicator"],
                         stdout=subprocess.PIPE)

    out = p.communicate()[0]
    for line in out.splitlines():
        if line.strip().isdigit():
            pid = int(line.strip())
            if pid != os.getpid():
                try:
                    os.kill(pid, signal.SIGUSR1)
                    util.log("Sent SIGUSR1 to process %u." % pid)
                    return True
                except Exception, e:
                    util.log("Error sending SIGUSR1 to process %u: %s" % (pid, e))
Example #9
0
    def merge_exported(self, tasks):
        """Merges data reported by task.  This is primarily used to get real
        urgency, maybe something else in the future."""
        out = util.run_command(["task", "rc.json.array=1", "export"])

        _tasks = {}
        for em in json.loads(out):
            _tasks[em["uuid"]] = em

        for idx, task in enumerate(tasks):
            if task["uuid"] not in _tasks:
                util.log("Warning: task {0} not exported by TaskWarrior.",
                         task["uuid"])
                continue

            _task = _tasks[task["uuid"]]
            if "urgency" in _task:
                tasks[idx]["urgency"] = float(_task["urgency"])

        return tasks
Example #10
0
    def update_task(self, task_id, properties):
        ts = int(time.time())

        # Use fresh data for missing fields, to prevent status changes etc.
        params = self.get_task_info(task_id)
        params.update(properties)
        params["modified"] = ts

        util.log("Task update: {0}", params)

        cur = self.conn.cursor()

        cur.execute(
            "UPDATE tasks SET modified = ?, project = ?, summary = ?, priority = ?, status = ?, description = ? WHERE id = ?",
            (params["modified"], params["project"], params["summary"],
             params["priority"], params["status"], params["description"],
             task_id))

        cur.execute(
            "INSERT INTO changes (task_id, ts, status, duration) VALUES (?, ?, ?, ?)",
            (task_id, ts, params["status"], 0))

        self.conn.commit()
Example #11
0
    def set_task_status(self, task_id, status):
        util.log("Changing status of task {0} to {1}.", task_id, status)

        cur = self.conn.cursor()
        ts = int(time.time())

        last = self.get_last_change(task_id)
        if last is not None:
            if status == last["status"]:
                return  # no changes
            duration = ts - int(last["ts"])
            cur.execute("UPDATE changes SET duration = ? WHERE id = ?",
                        (duration, last["id"]))
            util.log(
                "Task {0} spent {1} seconds in status {2}, switching to {3}.",
                task_id, duration, last["status"], status)

        cur.execute("UPDATE tasks SET modified = ?, status = ? WHERE id = ?",
                    (ts, status, task_id))
        cur.execute(
            "INSERT INTO changes (task_id, ts, status) VALUES (?, ?, ?)",
            (task_id, ts, status))
        self.conn.commit()
Example #12
0
    def load_data(self, database):
        """Reads the database file, parses it and returns a list of Task object
        instances, which contain all parsed data (values are unicode).

        This home-made parser returns raw timestamps, while 'task export'
        returns formatted UTC based dates which are hard to convert to
        timestamps to calculate activity duration, etc.

        TODO: find out a way to convert dates like '20130201T103640Z' to UNIX
        timestamp or at least a datetime.
        """
        _start = time.time()

        if not os.path.exists(database):
            util.log("Database {0} does not exist.", database)
            return {}

        with open(database, "rb") as f:
            raw_data = f.read()

        tasks = []
        for line in raw_data.rstrip().split("\n"):
            if not line.startswith("[") or not line.endswith("]"):
                raise ValueError("Unsupported file format " \
                    "in {0}".format(database))

            task = Task()
            for kw in shlex.split(line[1:-1]):
                if ":" not in kw:
                    util.log("Warning: malformed database token: {0}", kw)
                    continue
                k, v = kw.split(":", 1)
                v = v.replace("\/", "/")  # FIXME: must be a better way
                v = v.decode("utf-8")
                if k == "tags":
                    v = v.split(",")
                task[k] = v

            tasks.append(task)

        tasks = self.merge_exported(tasks)

        util.log("Task database read in {0} seconds.", time.time() - _start)

        return tasks
Example #13
0
 def on_toggle(self):
     util.log("on_toggle not handled")
Example #14
0
 def start_task(self, task_id):
     util.log("Starting task {0}.", task_id)
     util.run_command(["task", task_id, "start"])
Example #15
0
 def get_tasks(self):
     if self._tasks is None:
         util.log("Reloading tasks.")
         self._tasks = self.load_tasks()
     return self._tasks
Example #16
0
 def handle(*args, **kwargs):
     util.log("Got signal USR1, showing the search dialog.")
     self.search_dialog.show_all()
Example #17
0
 def stop_task(self, task_id):
     util.log("Stopping task {0}.", task_id)
     util.run_command(["task", task_id, "stop"], fail=False)
Example #18
0
 def finish_task(self, task_id):
     util.log("Finishing task {0}.", task_id)
     util.run_command(["task", task_id, "stop"], fail=False)
     util.run_command(["task", task_id, "done"])
Example #19
0
 def on_task_selected(self, task):
     util.log("task selected: %s" % task)
     if task:
         dialogs.Properties.show_task(self.database, task)
Example #20
0
 def on_pull(self):
     util.log("on_pull not handled")
Example #21
0
 def restart_task(self, task_id):
     util.log("Restarting task {0}.", task_id)
     util.run_command(["task", task_id, "mod", "status:pending"])
     util.run_command(["task", task_id, "start"])
Example #22
0
 def on_task_selected(self, task):
     util.log("on_task_selected not handled, %s" % task)
Example #23
0
 def on_stop_all(self):
     util.log("on_stop_all not handled")
Example #24
0
 def on_add_task(self):
     util.log("on_add_task not handled")
Example #25
0
 def setup_icon(self):
     util.log("WARNING: setup_icon not implimented")
Example #26
0
 def on_quit(self):
     util.log("on_quit not handled")