#!/usr/bin/python

# Copyright (C) Mark Eichin.
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the 3-clause BSD terms are met.
# (License subject to change.)

"""Hiveminder Braindump tag lister

Fetches all of your tags, in the (currently) cheapest possible way.
(At the moment that involves fetching all of your tasks...)
"""

__revision__ = "$Id: hive-cheap-tags.py,v 1.1 2008/01/05 03:32:00 eichin Exp $"
__version__ = "%s/%s" % (__revision__.split()[3], __revision__.split()[2])

import os
import urllib
import optparse
import sys
import re

try:
    import cElementTree as etree
except ImportError:
    try:
        import elementtree.ElementTree as etree
    except ImportError:
        import xml.etree.ElementTree as etree


# TODO: stolen from non-importable hive-braindump, fix that up
def my_sid(known_sid=[]):
    """fetch my sid from ~/.hiveminder"""

    if not known_sid:
        hive_file = os.path.expanduser("~/.hiveminder")
        for line in file(hive_file):
            if line.startswith("sid:"):
                known_sid.append(line.strip().split(":", 1)[-1].strip())
                break
        else:
            raise Exception("no sid found!")
    return known_sid[0]

def fetch_all_tags():
    """get back a tree of everything"""
    task_search = "http://hiveminder.com/=/search/BTDT.Model.Task/tags.xml"

    uo = urllib.FancyURLopener()
    uo.addheader("Cookie", "JIFTY_SID_HIVEMINDER=%s" % my_sid())

    u = uo.open(task_search)

    xmlresponse = u.read()
    try:
        response = etree.fromstring(xmlresponse)
    except Exception, xerr:     # xml.parsers.expat.ExpatError
        print "got", xerr, "parsing", xmlresponse
        raise

    tags = set()
    for tags_element in response.findall("value"):
        # TODO: filter out completed/deleted tasks, maybe?
        if tags_element.text:
            for tag in tags_element.text.split():
                tags.add(tag)

    return tags

def elisp_quote(s):
    """quote appropriately for appearing inline as an elisp strings"""
    s.replace('"', r'\"')
    return '"' + s + '"'

if __name__ == "__main__":
    parser = optparse.OptionParser(usage=__doc__, version="%%prog %s" % __version__)
    parser.add_option("--zero", "-0", "--print0", action="store_true")
    parser.add_option("--elisp", action="store_true")
    options, args = parser.parse_args()
    if args:
        parser.print_help()
        sys.exit(1)

    tags = fetch_all_tags()

    if options.elisp:
        print "(setq hiveminder-tags '("
    for tag in sorted(tags):
        if options.zero:
            sys.stdout.write(tag)
            sys.stdout.write('\0')
        elif options.elisp:
            print elisp_quote(tag)
        else:
            print tag
    if options.elisp:
        print "))"

