chiark / gitweb /
I'm sure I've done something since I remembered to commit...
[familyTree.git] / familyTree / askQuestion.py
index 8dbe0b1eabc81c58f98d77c3de4fce0b63e749c8..f7d60be3ded5f0a03a54ff2d4572e3b709f86142 100755 (executable)
@@ -5,243 +5,386 @@ import findYear
 from string import Template
 import cgi
 import re
+import pickle
+import pygraph.algorithms.accessibility as access
+import englishUtils as eU
+import printUtils as pU
+import graphQuestions as gQ
+import urllib2
+
+global presentYear 
+presentYear= 1000000
+global ageTable
+ageTable = "(SELECT diedYear-bornYear as age, name,ID,diedYear,bornYear"\
+       +" FROM people"\
+       +" WHERE bornYear<>0 AND diedYear<>0 AND (diedMonth>bornMonth"\
+       +" OR (diedMonth==0)"\
+       +" OR (diedMonth = bornMonth AND (diedDay>=bornDay OR diedDay =0)))"\
+        +" UNION"\
+               +" SELECT diedYear-bornYear-1 as age,name,ID,diedYear,bornYear"\
+        +" FROM people"\
+        +" WHERE bornYear<>0 AND diedYear<>0 AND diedMonth<>0"\
+       +" AND (diedMonth<bornMonth"\
+        +" OR (diedMonth = bornMonth AND (diedDay<bornDay AND diedDay <>0)))"\
+        +" )"
+
+global ageNowTable
+ageNowTable = "(SELECT strftime('%Y',date('now'))-bornYear as age,"\
+       +"  name,ID,diedYear,bornYear"\
+        +" FROM people"\
+        +" WHERE bornYear<>0  AND (strftime('%m',date('now'))>bornMonth"\
+        +" OR (strftime('%m',date('now')) = bornMonth AND"\
+       +" (strftime('%d',date('now'))>=bornDay)))"\
+        +" UNION"\
+        +" SELECT strftime('%Y',date('now'))-bornYear-1 as age,"\
+       +" name,ID,strftime('%Y',date('now')),bornYear"\
+        +" FROM people"\
+        +" WHERE bornYear<>0  AND (strftime('%m',date('now'))<bornMonth"\
+        +" OR (strftime('%m',date('now')) = bornMonth"\
+       +" AND (strftime('%d',date('now'))<bornDay)))"\
+        +" )"
+
+global ageChildTable
+ageChildTable = "(SELECT c.bornYear - p.bornYear as age,"\
+       +" c.name as cName,c.ID as cID,"\
+       +" p.name as pname,p.ID as pID,"\
+       +" c.bornYear as bornYear"\
+       +" FROM"\
+       +" parents INNER JOIN people c"\
+       +" ON parents.ID = c.ID"\
+       +" INNER JOIN people p"\
+       +" ON parents.parentID = p.ID"\
+       +" WHERE p.bornYear <>0 AND c.bornYear<>0"\
+       +" AND (c.bornMonth>p.bornMonth"\
+       +" OR (c.bornMonth = p.bornMonth AND c.bornDay>=p.bornDay))"\
+       +" UNION"\
+       +" SELECT c.bornYear - p.bornYear-1 as age,"\
+       +" c.name as cName,c.ID as cID,"\
+       +" p.name as pName,p.ID as pID,"\
+       +" c.bornYear as bornYear"\
+       +" FROM"\
+       +" parents INNER JOIN people c"\
+       +" ON parents.ID = c.ID"\
+       +" INNER JOIN people p"\
+       +" ON parents.parentID = p.ID"\
+       +" WHERE p.bornYear <>0 AND c.bornYear<>0"\
+       +" AND (c.bornMonth<p.bornMonth"\
+       +" OR (c.bornMonth = p.bornMonth AND c.bornDay<p.bornDay))"\
+       +" )"
+
 
-global link_Template 
-link_Template= Template(\
-       "<a href = http://www.chiark.greenend.org.uk/ucgi/~naath/$script"\
-       +" title=$title>$text</a>")
-def add_quotes(s):
-       s = str(s)
-       return "'"+s+"'"
 
 def run_query(s,t):
        c = make_cursor()
        return c.execute(s,t)
 
-def print_row(row,newLine):
+def make_insert(table,fields):
+
+        t = tuple(fields)
+        values = '('
+        for i in range(len(fields)):
+                values = values+'?,'
+        values = values[:-1]+')'
+
+        s = 'INSERT INTO '+table+' VALUES'\
+                +values
+        run_query(s,t)
+
+def number_people():
+       s = 'SELECT max(ID) FROM people;'
+       for r in run_query(s,()):
+               return int(r[0])
+
+def calendar(newLine):
        out = ''
-       for item in row:
-               out = out + str(item)+'|'
-       return out[:-1] + newLine
 
-def print_query(s,t,newLine):
-       printMe = ''
-       for row in run_query(s,t):
-               printMe = printMe + print_row(row,newLine)              
-       return printMe
-
-def is_number(s):
-    try:
-        float(s)
-        return 1
-    except ValueError:
-        return 0
-
-def print_tagged_query(relationship,s,t,newLine):
-       mine = ''
-       for row in run_query(s,t):
-               mine = mine + print_tagged_name(relationship,row,newLine)
-       return mine
+       mLength = [31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
+       b = 'born'
+       x = 'died'
+       fcstart = '<FONT COLOR = "'
+       fcmid = '">'
+       fcend = '</FONT>'
+       dcol = 'red'
+       dcstart = fcstart+dcol+fcmid
+
+       for m in range(12):
+
+               n = count_born_on(m+1,0,b)
+               o = count_born_on(m+1,0,x)
+               p = count_born_in(m+1,b)
+               q = count_born_in(m+1,x)
+
+               script = 'birthday.py?date=%d-0' %(m+1)
+               d = 0
+               url = pU.link_Template.substitute\
+                                (script = script,title = eU.month_numbers(m+1),\
+                                text = eU.month_numbers(m+1))
+               out += "%s %d %s%d%s %d %s%d%s%s" \
+                       %(url,n,dcstart,o,fcend,p,dcstart,q,fcend,newLine)
+
+
+               out+="<table>"
+               out+="<tr>"
+               for d in range(mLength[m]):
+                       script = 'birthday.py?date=%d-%d' % (m+1,d+1)
+                       url = pU.link_Template.substitute\
+                               (script = script,title = str(d+1),\
+                               text = str(d+1))
+
+                       n = count_born_on(m+1,d+1,b)
+                       o = count_born_on(m+1,d+1,x)
+       
+                       s = "<td>"
+                       e = "</td>"
+                       out+="%s%s%s %s%d%s %s%s%s%s%s " %(s,url,e,\
+                               s,n,e,s,dcstart,o,fcend,e)
+                       if (d+1)%7 ==0 or (d+1)==mLength[m]:
+                               out+="</tr>"
+                               out+="<tr>"
+               out+="</table>"
+               out+=newLine
 
+       script = 'birthday.py?date=0-0'
+        url = pU.link_Template.substitute\
+               (script = script,title = 'unknown',\
+                text = 'unkown')
 
-def relationship_html(ID,ID2,newLine):
-       if newLine=='<br>':
-               relationship = common_ancestors(ID,ID2,newLine)[2]
-                       
-               if relationship[-11:] != 'not related':
-                       script = "ancestors.py?ID=%s&ID2=%s" % (ID,ID2)
-                       url = link_Template.substitute\
-                               (script = script,title = "Common ancestors"\
-                                       ,text = "Common ancestors")
-                       return relationship + ' '+url + newLine
-               else:
-                       return relationship + newLine
-       else:
-               return ''
+       n = count_born_on(0,0,b)
+       o = count_born_on(0,0,x)
+       out+="%s %d %s%d%s%s" %(url,n,dcstart,o,fcend,newLine)
 
-def terr_html(terr,newLine,start,stop):
-       if newLine=='<br>':
-               if start == 0 and stop ==0:
-                       myTitle = add_quotes(terr)
 
-               else:
-                       s = "SELECT name,people.id"\
-                       +" FROM people INNER JOIN territories"\
-                       +" ON people.id = territories.id"\
-                       +" WHERE territory = ? AND stopyear <= ?"\
-                       +" ORDER BY startyear DESC;"
-
-                       t = (terr,start)
-                       myTitle = ''
-                       for row in run_query(s,t):
-                               myTitle += "previous - %s,%s" \
-                               % (row[0],row[1])
-                               break
 
-                       u = "SELECT name,people.id"\
-                        +" FROM people INNER JOIN territories"\
-                       +" ON people.id = territories.id"\
-                        +" WHERE territory = ? AND startyear >= ?"\
-                        +" ORDER BY startyear;"
-               
-                       v = (terr,stop)
-                        for r in run_query(u,v):
-                               myTitle += '&#xA next - %s,%s'\
-                               %(r[0],r[1])
-                                break
+       script = 'birthday.py?date=20-0'
+        url = pU.link_Template.substitute\
+                (script = script,title = 'on their birthday',\
+                text = 'on their birthday')
+       n = count_born_on(20,0,b)
+       out +="%d people died %s%s" %(n,url,newLine)
+
+
+       s = "select diedYear,count(*)"\
+                +" FROM people"\
+                +" WHERE diedYear==?"\
+                +" GROUP BY diedYear;"
+        for row in run_query(s,(presentYear,)):
+                out += pU.print_age_death_count(row,newLine)
+
+       for bd in ('born','died'):
+               out+=newLine
+               s = "SELECT "+bd+", count(*) AS n"\
+                       +" FROM (SELECT "+bd + "," + bd + "Year"\
+                       +" FROM people"\
+                       +" WHERE "+bd+"Month<>0 AND "+bd+"Day<>0)"\
+                       +" GROUP BY "+bd\
+                       +" HAVING n>1"\
+                       +" ORDER BY "+bd+"Year;"
+
+               t = "SELECT name,id"\
+                       +" FROM people"\
+                       +" WHERE "+bd+" = ?;"
+       
+
+               out += "On the following days more than one person %s: %s" \
+                       %(bd,newLine)
+
+               for row in run_query (s,()):
+                       out+=row[0]+":"+newLine
+                       for r in run_query(t,(str(row[0]),)):
+                               out+=pU.name_html(r,newLine)+newLine
+
 
-                       myTitle = add_quotes(myTitle)
 
-               return link_Template.substitute(\
-                       script = "territory.py?terr="+terr, title=myTitle,\
-                       text = terr)
+       return out
+
+def count_born_on(month,day,bd):
+       if month==20:
+               s = "SELECT count(*) FROM people"\
+                       +" WHERE bornMonth==diedMonth"\
+                       +" AND bornDay==diedDay"\
+                       +" AND bornMonth<>0"\
+                       +" AND diedDay<>0;"
+               t = ()
+
        else:
-               return terr
-def name_html(row,html):
-       if html=='<br>':
-               html=1
-       elif html=='\n':
-               html=0
-
-       if row[0] == None:
-               return row[1]
-       elif row[1]==0:
+               s = "SELECT count(*) FROM people"\
+                       +" WHERE "+bd+"Month==?"\
+                       +" AND "+bd+"Day==?"\
+                       +" AND "+bd+"Year<>?;"
+
+               t = (month,day,presentYear)
+
+       for row in run_query(s,t):
                return row[0]
-       else:
-               if html==1:
-                       script = "person.py?ID=%s" %(row[1])
-                       name = row[0]
-                       return link_Template.substitute(script = script\
-                               ,title = add_quotes(name),text = name)
-               else:
-                       return "%s,%s" % (row[0],row[1])
 
-def print_people(n):
-       if n>1:
-               return 'people'
-       else:
-               return 'person'
-def print_children(n):
-       if n>1:
-               return 'children'
-       else:   
-               return 'child'
-
-def print_age_child_count(row,newLine):
-       if newLine == '<br>':
-               script = "listAge.py?age=%s" % (row[0])
-               link = link_Template.substitute(script = \
-                       script, title = add_quotes(row[0]), text = row[0])
+def count_born_in(month,bd):
 
-               out = '%s %s had children at age %s %s'\
-                % (row[1],print_people(row[1]),link,newLine)
-               return out
-       else:
-               return print_row(row,newLine)
-
-def print_age_death_count(row,newLine):
-       if newLine =='<br>':
-               script = "listAgeDeath.py?age=%s" % (row[0])
-               link = link_Template.substitute(script = script,\
-                       title = add_quotes(row[0]),text = row[0])
-               out = "%s %s died at age %s %s " \
-                       %(row[1],print_people(row[1]), link,newLine)
-               return out
-       else:
-               return print_row(row,newLine)
+       s = "SELECT count(*) FROM people"\
+               +" WHERE "+bd+"Month==?"\
+               +" AND "+bd+"Year<>?;"
+       t = (month,presentYear)
 
-def print_name_count(row,newLine):
-       if newLine=='<br>':
-               script = "name.py?name=%s" % (row[0])
-               link = link_Template.substitute(script =\
-                       script, title = add_quotes(row[0]),text = row[0])
-               return "%s people called %s%s"\
-                       %(row[1],link, newLine)
-       else:
-               return print_row(row,newLine)   
+       for row in run_query(s,t):
+               return row[0]
 
-def print_children_count(row,newLine):
-       out = "%s %s had " % (row[0],print_people(row[0]))
+def born_on(date,newLine):
+       month = int(date.split('-')[0])
+       day = int(date.split('-')[1])
 
-       if newLine == '<br>':
-               script = "listChildCount.py?nc="+str(row[1])
-               link = link_Template.substitute(script =\
-                       script, title = add_quotes(row[1]),text = row[1])
+       fcstart = '<FONT COLOR = "'
+        fcmid = '">'
+        fcend = '</FONT>'
+        dcol = 'red'
+        dcstart = fcstart+dcol+fcmid
+
+
+       out = ''
+
+
+       if month==20:
+               n = count_born_on(month,day,'')
+
+               out+="%d %s died on their birthday: %s"\
+                       %(n, eU.print_people(n),newLine)
+
+               s =  "SELECT name,id,bornYear,diedYear,bornMonth,bornDay"\
+                       +" FROM people"\
+                       +" WHERE bornMonth==diedMonth"\
+                       +" AND bornDay==diedDay"\
+                       +" AND bornMonth<>0"\
+                       +" AND diedDay<>0"\
+                       +" ORDER BY diedYear-bornYear;"                 
+               t=()
+               out+="Died on the day they were born:%s"%(newLine)
+               out+=pU.table_header(['link','born and died'],newLine)
+               header=0
+               for row in run_query(s,t):
+                       if row[2]!=row[3] and header==0:
+                               header = 1
+                               out+=pU.table_foot(newLine)
+                               out+="%sDied on a later birthday:%s"\
+                                       %(newLine,newLine)
+                               out+=pU.table_header(['link','born','died','month','day'],\
+                                       newLine)
+                       link = pU.name_html(row,newLine)
+                       born = pU.print_year(row[2])
+                       died = pU.print_year(row[3])
+                       month = eU.month_numbers(row[4])
+                       day = str(row[5])
+                       if row[2]==row[3]:
+                               out+=pU.table_row([link,born],newLine)
+                       else:
+                               out+=pU.table_row([link,born,died,month,day],newLine)
+               out+=pU.table_foot(newLine)
+               return out
+
+       if day!= 0:
+               out += '%s %s %s' \
+               %(eU.month_numbers(month),eU.ordinal_numbers(day),newLine)
        else:
-               link = str(row[1])
+               out +='%s %s'\
+               %(eU.month_numbers(month),newLine)
 
-       out += "%s %s %s" % (link,print_children(row[1]),newLine)
 
-       return out
+       for bd in ['born','died']:
+               s = "SELECT name,id,"+bd+"Year FROM people"\
+                       +" WHERE "+bd+"Month==?"\
+                       +" AND "+bd+"Day==?"\
+                       +" AND "+bd+"Year<>?"\
+                       +" ORDER BY "+bd+"Year;"
 
-def print_tagged_name(relationship,row,newLine):
-       if row[0]==None:
-                       out = relationship + " not yet entered: " + row[1]
-               out = "%s not yet entered: %s" % (relationship,row[1])
-               else:
-               if newLine == '<br>':
-                       html = 1
-               else:
-                       html=0
-               if relationship =='':
-                       out = '%s   ' % (name_html(row,html))
+               t = (month,day,presentYear)
+               n = count_born_on(month,day,bd)
+               
+               if bd=='died':
+                       out+=dcstart
+               if day!=0:
+                       out+="%s %s %s on this day %s" \
+                       %(n,eU.print_people(n),bd, newLine)
+               elif month!=0:
+                       out+="%s %s %s in this month on unknown day %s"\
+                       %(n,eU.print_people(n),bd,newLine)
                else:
-                       out = relationship + ": " + name_html(row,html)
-                       out = '%s: %s' % (relationship,name_html(row,html))
-       return out + newLine
-
-def month_numbers(monthN):
-       if monthN == 0:
-               month ='unknown month'
-       elif monthN == 1:
-               month ='January'
-       elif monthN==2:
-               month ='February'
-       elif monthN==3:
-               month ='March'
-       elif monthN==4:
-               month ='April'
-       elif monthN==5:
-               month ='May'
-       elif monthN==6:
-               month ='June'
-       elif monthN==7:
-               month ='July'
-       elif monthN==8:
-               month ='August'
-       elif monthN==9:
-               month ='September'
-       elif monthN==10:
-               month ='October'
-       elif monthN==11:
-               month ='November'
-       elif monthN==12:
-               month ='December'
-       else:
-               month = 'Incorrectly entered month ' + str(monthN)
-       return month
-
-def ordinal_numbers(number):
-       number = int(number)
-       out = '%d' % (number)
-       if number % 10==1 and number/10 % 10 !=1:
-               out +='st'
-       elif number % 10==2 and number/10 % 10 !=1:
-               out +='nd'
-       elif number % 10==3 and number/10 % 10 !=1:
-               out +='rd'
-       else:
-               out +='th'
+                       out+="%s %s %s in unknown month on unknown day %s"\
+                       %(n,eU.print_people(n),bd,newLine)
+               if bd=='died':
+                       out+=fcend
+               out+=pU.table_header(['id','link',bd],newLine)
+               for row in run_query(s,t):
+                       y = pU.print_year(row[2])
+
+                       link = pU.name_html(row,newLine)
+                       out+=pU.table_row([row[1],link,y],newLine)
+
+               out+=pU.table_foot(newLine)
+               out+=newLine
+
+       if day==0 and month!=0:
+               for bd in ['born','died']:
+                       s = "SELECT name,id,"+bd+"Year FROM people"\
+                        +" WHERE "+bd+"Month==?"\
+                        +" AND "+bd+"Year<>?"\
+                        +" ORDER BY "+bd+"Year;"
+
+                       t = (month,presentYear)
+                       n = count_born_in(month,bd)     
+
+                       if bd=='died':
+                               out+=dcstart
+                       out+="%s %s %s in this month %s" \
+                               %(n,eU.print_people(n),bd, newLine)
+                       if bd=='died':
+                               out+=fcend
+
+                       out+=pU.table_header(['link',bd],newLine)
+                       for row in run_query(s,t):      
+                               link = pU.name_html(row,newLine)
+                               y = pU.print_year(row[2])
+
+                               out+=pU.table_row([link,y],newLine)
+                       out+=pU.table_foot(newLine)
+                       out+=newLine
+                                       
        return out
 
-def list_territories(newLine):
-       s = "SELECT DISTINCT territory"\
-       +" FROM territories"\
-       +" ORDER BY territory;"
 
-       out = ''
-       for row in run_query(s,()):
-               out += terr_html(row[0],newLine,0,0) +newLine
+def alive_on(day,month,year,newLine):
+
+       bornBefore = "(bornMonth<? OR"\
+                       +" (bornMonth==? AND bornDay<=?))"
+
+       diedAfter = "(diedMonth>? OR diedMonth==0"\
+                       +" OR (diedMonth==? AND (diedDay>=? OR diedDay==0)))"
+
+       bornOrder = "bornyear,bornmonth,bornday"
+       diedOrder = "diedyear,diedmonth,diedday"
+       s = "SELECT name,ID,bornYear,diedYear FROM people"\
+               +" WHERE"\
+               +" bornYear<>0 AND diedYear<>0 AND("\
+               +" (bornYear<? AND diedYear>?)"\
+               +" OR"\
+               +" (bornYear==? AND diedYear>? AND "+bornBefore+")"\
+               +" OR"\
+               +" (bornYear<? AND diedYear==? AND "+diedAfter+")"\
+               +" OR"\
+               +" (bornYear==? and diedYear==? AND "\
+               +bornBefore+" AND "+diedAfter+")"\
+               +")"\
+               +"ORDER BY "+bornOrder+"," + diedOrder+";"
+
+       yeart = (year,year)
+       bbt=(month,month,day)
+       dat = (month,month,day)
+       t = yeart+yeart+bbt+yeart+dat+yeart+bbt+dat     
+       out=pU.table_header(['link','born','died'],newLine)
+       for row in run_query(s,t):
+               link=pU.name_html(row,newLine)
+               born = pU.print_year(row[2])
+               died = pU.print_year(row[3])
+               out+=pU.table_row([link,born,died],newLine)
+
+       out+=pU.table_foot(newLine)
+
        return out
 
 def list_people_parents():
@@ -254,7 +397,7 @@ def list_people_parents():
 
                ID = row[1]
                [parents, parentIDs,parentNames] = find_parents(ID)
-               [spouses,spousesID,spousesNames] = find_spouses(ID)
+               [spouses,spousesID,spousesNames,sD] = find_spouses(ID)
                
                [self,myID,myName] = find_person(ID)
                output.append([self,parents,spouses])
@@ -262,542 +405,1097 @@ def list_people_parents():
 
 
 def list_people(newLine):
-       s = "SELECT name,id,bornyear"\
+       s = "SELECT name,id,bornyear,fullname,diedYear,url"\
        +" FROM people"\
-       +" ORDER BY bornyear;"
+       +" ORDER BY bornyear,diedYear;"
 
-       out = ''
+       out = pU.table_header(['ID','link','wiki','name','born','died'],\
+               newLine)
        year = 0
-       out = out + 'born in unknown year:' +newLine
+       out+=pU.table_row(['','',\
+               '<b>Unknown Year</b>',0,0,''],newLine)
        for row in run_query(s,()):
                if row[2]!=0 and row[2]/100==0:
-                       out +='%sborn in 1st century:%s' % (newLine,newLine)
-
+                       out+=pU.table_row(['','','',\
+                       '<b>1st century</b>'\
+                       ,1,100],newLine)
                if row[2]/100!=year/100:
                        century = row[2]/100 + 1
-                       out +='%sborn in %s century: %s'\
-                        %(newLine,ordinal_numbers(century),newLine)
+                       start = century * 100 -99
+                       end = century * 100
+                       out+=pU.table_row(['','','',\
+                        '<b>'+eU.ordinal_numbers(century)+' century</b>',\
+                               start,end],newLine)
 
+               
+               ID = row[1]
+               link = pU.name_html(row,newLine)
+#              if row[5] != '.':
+#                      struct = fetch_page(row[5])
+#                      if struct.has_key('query'):
+#                              pName = struct['query']['pages'].keys()[0]
+#                              wikiName = struct['query']['pages'][pName]['title']
+#                      else:
+#                              wikiName = row[5]
+#              else:
+#                      wikiName = ''
+               wikiName = row[5]
+               wikiLink = "<a href='" + wikiName + "'>"+wikiName+"</a>"
+
+               a = re.search('#',wikiName)
+               if a:
+                       wikiName = '#'
+                       wikiLink = wikiName
+               if row[5]=='.':
+                       wikiName = 'None'
+                       wikiLink = wikiName
+
+
+               name = row[3]
+               born = pU.print_year(row[2])
+               died = pU.print_year(row[4])
+
+               out+=pU.table_row([ID,link,wikiLink,name,born,died],newLine)
+               year = row[2]
+       out+=pU.table_foot(newLine)
+       return out
 
-               out+= name_html(row,newLine) +newLine
+def list_page(newLine):
+       s = "SELECT name,ID,url FROM people ORDER BY ID;"
+       t = ()
+       out = ''
 
-               if row[2] == 0: #unknown year
+       check=[]
+       for row in run_query(s,t):
+               if row[2]!='.':
+                       topLink = "%d   <a href='%s'>%s</a>" %(row[1],row[2],row[0])
+                       print row[1]
+                       myLink = pU.name_html(row,newLine)
+                       topLink = topLink+' '+myLink
+                       url = row[2]
+                       id = row[1]
+                       
+                       [fam,count,checkMe] = find_fam(id,url,newLine)
+                       if checkMe==0:
+                               out+=topLink+newLine+fam+newLine
+                       else:
+                               check.append([id,topLink,url,fam,count])
+
+       outDone = out
+       out = 'MATCHED'+newLine
+       hold = 'CHECK COUNT'+newLine
+       checkAgain=[]
+       for p in check:
+               id = p[0]
+               topLink=p[1]
+               url=p[2]
+               fam=p[3]
+               countF = p[4]
+               print id
+       
+               links,countL = find_links(url)
+               if links:
+                       if links[0]!=-1:
+                               this=topLink+newLine+fam+newLine
+
+                               this+='<ul>'
+                               for l in links:
+                                       this+='<li>'+l+newLine+'\n'
+                               this+='</ul>'
+                               good=1
+                               for i in range(3):
+                                       if countL[i]<countF[i]:
+                                               good = 0;
+                               if good==1:
+                                       out+=this
+                               else:
+                                       hold+=\
+                       this+newLine+str(countF)+str(countL)+newLine
 
-                       t = (row[1],) #person ID
+                       else:
+                               checkAgain.append(p)
+               else:
+                               checkAgain.append(p)
+       outMatched = out
+       outUnMatched = hold
 
+       out=newLine + 'CHECK NO INFO'+newLine
+       for p in checkAgain:
+               id = p[0]
+                topLink=p[1]
+                url=p[2]
+                fam=p[3]
+               print id
 
-                       #died
-                       u = "SELECT diedyear FROM people WHERE ID = ?;"
+               if re.search('#',url):
+                       continue
+               out+=topLink+newLine+fam
 
-                       bornAfter = 0
-                       bornBefore = 0
-                       for r in run_query(u,t):
-                               if r[0] !=0:
-                                       bornAfter = r[0] -100
-                                       bornBefore = r[0]
-                                       out += "Died: %s %s"\
-                                       %(r[0],newLine)
-                       #find children
-                       u = "Select people.bornYear from"\
-                               +" people INNER JOIN parents"\
-                               +" ON people.ID = parents.ID"\
-                               +" WHERE parents.parentID = ?"\
-                               + " ORDER BY people.bornYear;"
-                       
-                       hadChild=[]
-                       
-                       for r in run_query(u,t):
-                               if r[0] != 0:
-                                       hadChild.append(r[0])
-                       
-                       if len(hadChild)!=0:
-                               out += "had children in: "
-                               for c in hadChild:
-                                       out+= '%s,' % (c)
-                               out = out[:-1] + newLine
-                               bornBefore = hadChild[0]-12
-                               if bornAfter==0:
-                                       bornAfter = hadChild[0]-100
-                       
-                       u = "Select styles.startYear, styles.style from"\
-                                +" people INNER JOIN styles"\
-                                +" ON people.ID = styles.ID"\
-                                +" WHERE people.ID = ? and"\
-                                +" styles.startYear <>0"\
-                                +" ORDER BY styles.startYear;"
-
-                        for r in run_query(u,t):
-                               out += "%s from %s %s"\
-                                       %(r[1],r[0],newLine)
-                               if bornAfter ==0:
-                                       bornAfter = r[0] -100
-                                break
-
-                       if bornAfter!=0:
-                               if bornBefore == 0: 
-                                       out += "probably born after %s"\
-                                               %(bornAfter)
+       return [outDone,outMatched,outUnMatched,out]
+
+def find_fam(id,link,newLine):
+       out = ''
+
+       [parents, parentIDs,parentNames] = find_parents(id)
+       [spouses,spousesID,spousesNames,sD] = find_spouses(id)
+       [nodes,IDs,names,childrenBorn] = \
+               find_children(id)
+       
+       relIDs = parentIDs+spousesID
+       for ID in IDs:
+               relIDs.append(ID[0])
+
+       out+='<ul>'
+       findUrl = 'SELECT url,name FROM people WHERE ID=?'
+       findName = 'SELECT name,ID FROM people WHERE ID=?'
+       anyCheck = 0;
+       count = [0, 0, 0]
+       for ID in relIDs:
+               t = (ID,)
+               if ID in parentIDs:
+                       type = 'parent'
+                       count[0]+=1
+               elif ID in spousesID:
+                       type = 'spouse'
+                       count[1]+=1
+               else:
+                       type = 'child'
+                       count[2]+=1
+
+               for row in run_query(findUrl,t):
+                       url = row[0]
+
+                       if url!='.':
+                               url = row[0]
+                               title = row[1]
+                               out+='<li>'+type+" <a href="+url\
+                               +">"+title+"</a>"+newLine
+                       else:
+                               for row in run_query(findName,t):
+#                                      out+='<li>'+pU.name_html(row,newLine)\
+#                                      +'CHECK'+newLine
+                                       name=row[0]
+                                       id = str(row[1])
+                                       out+='<li>'+type+' '+name + ' '+id+\
+                                               ' CHECK'+newLine
+                                       anyCheck = 1
+               
+       out+='</ul>'
+       return [out,count, anyCheck]
+
+def fetch_page(url):
+       import json
+
+       title = url.split('/')[-1]
+        url = 'http://en.wikipedia.org/w/api.php?'\
+                +'format=json&action=query'\
+                +'&titles='+title\
+                +'&prop=revisions&rvprop=content&redirects'
+
+        r = urllib2.urlopen(url)
+        t = r.read()
+        jd = json.JSONDecoder()
+       struct = jd.decode(t)
+
+
+       return struct
+
+def find_infoBox(url):
+       struct = fetch_page(url)
+       try:
+               pages = struct['query']['pages'].keys()
+       except:
+               return
+
+        startPatt = re.compile('{{',re.DOTALL)
+        endPatt = re.compile('}}',re.DOTALL)
+        infoboxPatt = re.compile('{{( )*[Ii]nfobox',re.DOTALL)
+
+       isIBOX = 0
+       for p in pages:
+               try:
+                       page = struct['query']['pages'][p]['revisions'][0]['*']
+               except:
+                       return
+
+               title = struct['query']['pages'][p]['title']            
+               iBox = re.search(infoboxPatt,page)
+                starts = re.finditer(startPatt,page)
+               ends = re.finditer(endPatt,page)
+
+               if iBox==None:  
+                       continue
+
+               myStart = iBox.start()
+               isIBOX=1
+                                       
+               countMe = 0
+               start = -1
+                while start<myStart:
+                       start = starts.next().start()
+                       end = -1
+                while end<myStart:
+                       end = ends.next().start()
+                while 1==1:
+                       if start<end:
+                               countMe+=1
+                               start = starts.next().start()
+                       elif end<start:
+                               countMe-=1
+                               myEnd = end
+                               end = ends.next().start()
+                       if countMe==0:
+                               break
+               info = page[myStart+2:myEnd]
+
+       if isIBOX==1:
+               return info
+       else:
+               return 
+
+def find_links(url):
+
+       info = find_infoBox(url)
+
+       if info:
+               l,c = wikilink_box(info)
+               return l,c
+       else:
+               return [-1],[]  
+
+def wikilink_box(text):
+       linkPatt = "([^=]*?)\[\[(.*?)\]\](.*?)"
+       #linkPatt = "\|(.*?)\[\[(.*?)\]\](.*?)\n"       
+       #linkPatt = "(.*?)\[\[(.*?)\]\]([^<]*?)[\\n|<br.*?>|,]"
+       links = []
+
+       commentPatt = "<!--.*?>"
+       sizePatt = "<[/]*small>"
+       text=re.sub(commentPatt,'',text)
+       text = re.sub(sizePatt,'',text)
+
+       pscPatt = "father|mother|parent|spouse|issue|child"
+       typePatt = "(.*?)="
+       lines = re.split('\\n',text)
+       count = [0, 0,0]
+       for line in lines:
+               if re.search(pscPatt,line):
+                       t = re.search(typePatt,line)
+                       if t is None:
+                               continue
+                       type = t.group(1)
+                       if re.search('father|mother|parent',type):
+                               c=0
+                       elif re.search('spouse',type):
+                               c=1
+                       else:
+                               c=2
+                       people = re.split('<br.*?>',line)
+                       for p in people:
+                               count[c]+=1
+                               if re.search(linkPatt,p):
+                                       l = re.search(linkPatt,p)
+                                       url = wiki_to_url(l.group(2))
+                                       t = l.group(2).split('|')[-1]
+
+                                       myLink = '<a href="%s">%s</a>' \
+                                       %(url,t)
+                                       link = l.group(1)+myLink+l.group(3)
+                                       add=type+link
                                else:
-                                       out +="probably born between %s and %s"\
-                                               %(bornAfter, bornBefore)
-                               out = out + newLine
+                                       add = type+' '+p
+                               links.append(add)
+       return links,count
 
-               year = row[2]
-       return out
 
-def count_names(newLine):
-       s = "SELECT firstName, count(*)"\
-       +" FROM people"\
-       +" GROUP BY firstName"\
-       +" ORDER BY count(*) DESC;"
+def wiki_to_url(wiki):
+       base = 'https://en.wikipedia.org/wiki/'
+       u = wiki.split('|')[0]
+       u = re.sub(' ','_',u)
 
-       out = ''
-       for row in run_query(s,()):
-               out += print_name_count(row,newLine)
+       return base+u   
 
-       return out
+def check_true(newLine):
+       s = "SELECT name,id,url,born,died FROM people WHERE id>? and id<? ORDER BY id;"
+       t = (0,5000)
 
+       out='<table border = "1" style = "width:100%">'
+       out+='<tr>'
+       out+='<th style="width:20%">Name</th>'
+       out+='<th style="width:40%">Toy</th>'
+       out+='<th style="width:40%">Wiki</th>'
+       out+='</tr>'
 
+       for row in run_query(s,t):
+               if row[2]=='.':
+                       continue
+               struct = fetch_page(row[2])
+               try:
+                       p = struct['query']['pages'].keys()[0]
+               except:
+                       continue
+
+               title = struct['query']['pages'][p]['title']            
+                               
+               topLink = "%d   <a href='%s'>%s</a>" %(row[1],row[2],title)
+               
+               myLink = pU.name_html(row,newLine)
+               topLink = topLink+newLine+myLink
+               url = row[2]
+               id = row[1]
+                       
+               [fam,count,checkMe] = find_fam(id,url,newLine)
+               infobox = find_infoBox(url)
 
-def count_children(newLine):
 
-       s = "SELECT count(*),nc"\
-       +" FROM ("\
-       +" SELECT count(*) AS nc"\
-       +" FROM parents"\
-       +" GROUP BY parentID"\
-       +" HAVING parentID <>'?'"\
-       +" AND parentID <> '0')"\
-       +" GROUP BY nc;"
+               if checkMe!=0:
+                       continue
+               out+='<tr>'
+               out+='<td>'+topLink+'</td>'
+       
+               if infobox is None:
+                       out+='</tr>'
+                       continue
 
-       out = ''
-       for row in run_query(s,()):
-               out += print_children_count(row,newLine)
-       return out
+               
 
-def parents_with_children(nChildren,newLine):
-       s = "SELECT name,parentID"\
-       + " FROM parents"\
-       + " LEFT JOIN people"\
-       + " ON parentID = people.ID"\
-       + " GROUP BY parentID"\
-       + " HAVING count(*) = ?"\
-       + " AND parentID <> 0"\
-       + " ORDER BY bornYear;"
+               out+='<td>'+fam+newLine+'born:'+row[3]+newLine\
+                       +'died:'+row[4]+'</td>'
 
 
-       u = "SELECT count(*)"\
-       +" FROM  parents INNER JOIN people"\
-       +" ON parents.ID = people.ID"\
-       +" WHERE parentID = ?"\
-       +" AND (diedyear-bornyear>? OR died='present');"
+               wikiLink='\\[\\[([^\\|\\]]*)\\|*(.*?)\\]\\]'
+               htmlLink=r'<a href="https://en.wikipedia.org/wiki/\1">\1</a>'
 
-       out = "People who had %s %s:%s" \
-               %(nChildren,print_children(nChildren),newLine)
+               htmlBox = re.sub(wikiLink,htmlLink,infobox)
 
-       for row in run_query(s,(nChildren,)):
-               out += name_html(row,newLine)
-               for r in run_query(u,(row[1],1)):       
-                       out += " %d  survived infancy" % r[0]
-               for r in run_query(u,(row[1],18)):
-                       out += " and %s survived to adulthood" % r[0]
-               out = out +newLine
+               place = 0
+               starts = re.finditer('{{',htmlBox)
+               stops = re.finditer('}}',htmlBox)
+               last = len(htmlBox)             
+
+               try:
+                       start = starts.next().start()
+                       stop = stops.next().start()
+               except:
+                       start = last
+                       stop = last
+
+               lines=[]
+               inList= 0
+
+               for i in re.finditer('\|',htmlBox):
+                       if i.start()>start and start<stop:
+                               inList+=1
+                               try:
+                                       start= starts.next().start()
+                               except:
+                                       start = last
+                       elif i.start()>stop and stop<start:
+                               inList-=1
+                               try:
+                                       stop = stops.next().start()
+                               except:
+                                       stop = last
+
+                       if inList==0:
+                               lines.append(htmlBox[place:i.start()])
+                               place = i.start()
+
+                       
+               of_interest = 'father|mother|parent|child|issue'\
+                       +'|spouse|birth_date|death_date'
        
+               out+='<td>'
+
+               parents = []
+               children=[]
+               spouse=[]
+               dates=[]
+
+               for l in lines:
+                       if re.search('father|mother|parent',l):
+                               parents.append(l)
+                       if re.search('child|issue',l):
+                               children.append(l)
+                       if re.search('spouse',l):
+                               spouse.append(l)
+                       if re.search('birth_date|death_date',l):
+                               dates.append(l)
+
+               for p in parents:
+                       out+=p+newLine
+               for s in spouse:
+                       out+=s+newLine
+               for c in children:
+                       out+=c+newLine
+               for d in dates:
+                       out+=d+newLine
+
+               out+='</td></tr>'
+
+       out+='</table>'
        return out
 
+
+
+
 def search_name(name,newLine):
-       s = "SELECT name, ID"\
+       s = "SELECT name, people.ID,fullname,BornYear,DiedYear"\
         +" FROM people"\
-        +" WHERE name LIKE ?;"
+        +" WHERE fullname LIKE ? or name LIKE ?"\
+       +" ORDER BY BornYear;"
+
+       s2 = "SELECT family FROM families where ID=?"
 
        IDs=[]
        names=[]
 
        out = 'Names starting with %s:%s' % (name,newLine)
-       t = (name + '%',)
+       t = (name + '%',name+'%')
        fullIDs=[]
+       out+=pU.table_header(['link','name','born','died','family'],newLine)
        for row in run_query(s,t):
-                out += name_html(row,newLine) + newLine
+               b = pU.print_year(row[3])
+               d = pU.print_year(row[4])
+
+               id = row[1]
+               fams=''
+               for r in run_query(s2,(id,)):
+                       fams+=r[0]+' '
+
+               out+=pU.table_row([pU.name_html(row,newLine),row[2],b,d,fams],\
+                       newLine)
+
                fullIDs.append(row[1])
                names.append(row[0])
                IDs.append(row[1])
+       out+=pU.table_foot(newLine)
 
-        t = ('%' + name + '%',)
+        t = ('%' + name + '%','%'+name+'%')
        out += '%sNames containing %s:%s' %(newLine,name,newLine)
+       out+=pU.table_header(['link','name','born','died','family'],newLine)
         for row in run_query(s,t):
                if row[1] not in fullIDs:
-                       out += name_html(row,newLine) + newLine
-                       names.append(row[0])
+                       b = pU.print_year(row[3])
+                       d = pU.print_year(row[4])
+
+                       id = row[1]
+                       fams=''
+                       for r in run_query(s2,(id,)):
+                               fams+=r[0]+' '
+
+                       out+=pU.table_row([pU.name_html(row,newLine),\
+                               row[2],b,d,fams],newLine)
+                       names.append(row[0]+','+row[2])
                        IDs.append(row[1])
+       out+=pU.table_foot(newLine)
+
+       s = '''SELECT name,people.ID,style,fullname,bornYear, diedYear,
+       startYear,stopYear,family
+       FROM people INNER JOIN styles
+       ON styles.id = people.id
+       LEFT JOIN families ON people.ID = families.ID
+       WHERE style LIKE ?
+       ORDER BY bornYear;'''
        
-       s = "SELECT name,people.ID,style"\
-       +" FROM people INNER JOIN styles"\
-       +" ON styles.id = people.id"\
-       +" WHERE style LIKE ?;"
        out += '%sStyles containing %s:%s' %(newLine,name,newLine)
+       out+=pU.table_header(['link','name','born',\
+               'died','style','from','to','family'],newLine)
+       t = (t[0],)
        for row in run_query(s,t):
-               out +="%s %s %s" %(name_html(row,newLine),row[2],newLine)
+               b = pU.print_year(row[4])
+               d = pU.print_year(row[5])
+               start = pU.print_year(row[6])
+               stop = pU.print_year(row[7])
+               out+=pU.table_row([pU.name_html(row,newLine),\
+                       row[3],b,d,row[2],start,stop,row[8]],newLine)
+
+       out+=pU.table_foot(newLine)
         return [out,names,IDs]
 
+def count_names(newLine):
+       s="SELECT names.name, count(*),"\
+       +" min(nullif(bornYear,0)),max(nullif(bornYear,0))"\
+       +" FROM names INNER JOIN people on people.ID = names.id"\
+       +" group by names.name"\
+
+
+       t = "SELECT count(*) FROM people WHERE firstName = ?"
+       
+       out=pU.table_header(\
+               ['name','count','earliest born',\
+               'latest born','range','count as first name'],\
+               newLine)
+       for row in run_query(s,()):
+               for r in run_query(t,(row[0],)):
+                       c =r[0]
+               if row[3] is not None and row[2] is not None:
+                       range = row[3]-row[2]
+               else:
+                       range = None
+               out+=pU.print_name_count(row,range,c,newLine)
+       out+=pU.table_foot(newLine)
+       
+       return out
 
 def people_with_name(name,newLine):
-       s = "SELECT name, ID"\
+       s = "SELECT name, ID,fullname,bornYear,diedYear"\
        +" FROM people"\
-       +" WHERE firstname = ?;"
-
-       out = ''
+       +" WHERE firstname = ?"\
+       +" ORDER BY bornYear;"
 
        t = (name,)
 
+       out='As a first name'+newLine
+       out += pU.table_header(['ID','name','link','born','died'],newLine)
+       for row in run_query(s,t):
+               myName = pU.name_html(row,newLine)
+               by = pU.print_year(row[3])
+               dy = pU.print_year(row[4])
+               
+               out+=pU.table_row([row[1],row[2],myName,by,dy],newLine)
+
+       out+=pU.table_foot(newLine)
+
+       s = "SELECT people.name, people.ID,fullname,bornYear,diedYear"\
+       +" FROM people"\
+       +" LEFT JOIN names ON people.ID = names.ID"\
+       +" WHERE names.name=? AND firstName<>?"\
+       +" ORDER BY bornYear;"
+
+       t = (name,name)
+       out+=newLine+'As a middle name'+newLine
+       out +=pU.table_header(['ID','name','link','born','died'],newLine)
        for row in run_query(s,t):
-               out += name_html(row,newLine) + newLine
+               myName = pU.name_html(row,newLine)
+               by = pU.print_year(row[3])
+               dy = pU.print_year(row[4])
+               
+               out+=pU.table_row([row[1],row[2],myName,by,dy],newLine)
+
+       out+=pU.table_foot(newLine)
+       
+
 
        return out
 
-def count_birth_month(newLine):
-       s = "SELECT bornMonth, count(*)"\
-               +" FROM people"\
-               +" GROUP BY bornMonth"\
-               +" ORDER BY bornMonth;"
 
-       t = "SELECT * FROM people WHERE bornMonth = ?;"
+def count_children(newLine):
+
+       s = "SELECT count(*),nc"\
+       +" FROM ("\
+       +" SELECT count(*) AS nc"\
+       +" FROM parents INNER JOIN people ON parentID = people.ID"\
+       +" GROUP BY parentID"\
+       +" HAVING parentID <>'?'"\
+       +" AND parentID <> '0')"\
+       +" GROUP BY nc;"
 
        out = ''
        for row in run_query(s,()):
-               month = month_numbers(row[0])
-               out += "%s:%s%s" %( month,row[1],newLine)
-
-               if row[0]>12:
-                       u = (row[0],)
-                       out +=print_query(t,u,newLine)
-               
+               out += pU.print_children_count(row,newLine)
        return out
 
-def count_death_month(newLine):
-        s = "SELECT diedMonth, count(*)"\
-                +" FROM people"\
-                +" GROUP BY diedMonth"\
-                +" ORDER BY diedMonth;"
+def parents_with_children(nChildren,newLine):
+       s = "SELECT name,parentID"\
+       + " FROM parents"\
+       + " INNER JOIN people"\
+       + " ON parentID = people.ID"\
+       + " GROUP BY parentID"\
+       + " HAVING count(*) = ?"\
+       + " AND parentID <> 0"\
+       + " ORDER BY bornYear;"
 
-       t = "SELECT * FROM people WHERE diedMonth = ?;"
 
-        out = ''
-        for row in run_query(s,()):
-                month = month_numbers(row[0])
-                out += '%s:%s%s'%(month,row[1], newLine)
+       u = "SELECT count(*)"\
+       +" FROM  parents INNER JOIN people"\
+       +" ON parents.ID = people.ID"\
+       +" WHERE parentID = ?"\
+       +" AND (diedyear-bornyear>? OR died='present');"
 
-               if row[0]>12:
-                        u = (row[0],)
-                        out +=print_query(t,u,newLine)
+       out = "People who had %s %s:%s" \
+               %(nChildren,eU.print_children(nChildren),newLine)
+
+       out+=pU.table_header(['link','survived infancy','survived to adulthood'],newLine)
+       for row in run_query(s,(nChildren,)):
+               link = pU.name_html(row,newLine)
+               for r in run_query(u,(row[1],1)):       
+                       infant = r[0]
+               for r in run_query(u,(row[1],18)):
+                       adult = r[0]
+               out +=pU.table_row([link,infant,adult],newLine)
+       out+=pU.table_foot(newLine)
+       return out
 
-        return out
 
 def count_age_at_child(newLine):
 
-       s = "select p1.bornYear - p2.bornYear as age, count(*)"\
-               +" FROM"\
-               +" parents INNER JOIN people p1"\
-               +" ON parents.ID = p1.ID"\
-               +" INNER JOIN people p2"\
-               +" ON parents.parentID = p2.ID"\
-               +" WHERE p1.bornYear <> 0 and p2.bornYear<>0"\
-               +" GROUP BY age;"
+       s = "SELECT age,count(*)"\
+               +" FROM "+ageChildTable\
+               +" GROUP BY age ORDER BY age;"
 
        out = ''
        for row in run_query(s,()):
-               out +=print_age_child_count(row,newLine)
+               out +=pU.print_age_child_count(row,newLine)
 
        return out
 
 def people_had_child_at_age(age,newLine):
 
-       s = "select p1.bornYear - p2.bornYear as age, p1.name, p1.ID"\
-                +",p2.name,p2.ID FROM"\
-                +" parents INNER JOIN people p1"\
-                +" ON parents.ID = p1.ID"\
-                +" INNER JOIN people p2"\
-                +" ON parents.parentID = p2.ID"\
-               +" WHERE age = ? AND p1.bornYear<>0 AND p2.bornYear<>0"
 
-       t = (int(age),)
+       s = "SELECT age,cname,cID,pname,pID,bornYear"\
+               +" FROM "+ageChildTable\
+               +" WHERE age = ?;"
 
-       out = ''
+       t = (int(age),)
        out = 'At age ' + str(age) + ' :'
+       out+=pU.table_header(['parent','child','year'],newLine)
        for row in run_query(s,t):
-               parent = name_html([row[3],row[4]],newLine)
-               child = name_html([row[1],row[2]],newLine)
-               out += "%s%s had %s" % (newLine,parent,child)
+               parent = pU.name_html([row[3],row[4]],newLine)
+               child = pU.name_html([row[1],row[2]],newLine)
+               year = pU.print_year(row[5])
+               out+=pU.table_row([parent,child,year],newLine)
+#              out += "%s%s had %s" % (newLine,parent,child)
+       out+=pU.table_foot(newLine)
        return out
 
 def count_age_at_death(newLine):
-       s = "select diedYear-bornYear as age,count(*)"\
-               +" FROM people"\
-               +" WHERE diedYear<>0 AND bornYear<>0"\
+
+
+       s = "SELECT age,count(*)"\
+               +" FROM"\
+               + ageTable\
+               +" WHERE diedYear<>?"\
                +" GROUP BY age;"
+
        out=''
-       for row in run_query(s,()):
-               out += print_age_death_count(row,newLine)
+       for row in run_query(s,(presentYear,)):
+               out += pU.print_age_death_count(row,newLine)
+
+       s = "select diedYear,count(*)"\
+               +" FROM people"\
+               +" WHERE diedYear==?"\
+               +" GROUP BY diedYear;"
+       for row in run_query(s,(presentYear,)):
+               out += pU.print_age_death_count(row,newLine)
 
        return out
 
 def people_died_at_age(age,newLine):
-       s = "SELECT diedYear-bornYear as age, name,ID"\
-               +" FROM people"\
-               +" WHERE age = ? AND bornYear<>0 AND diedYear<>0;"
-       t = (int(age),)
-       out =''
-       out = 'These people died at age ' +str(age) + ' :'
-       for row in run_query(s,t):
-               out += newLine+ name_html([row[1],row[2]],newLine)
+       
+
+       if age != str(presentYear):
+
+               s = "SELECT age,name,ID,diedYear,bornYear"\
+               +" FROM "\
+               + ageTable\
+               +" WHERE age = ?"\
+               +" ORDER BY diedYear;"
+
+
+               t = (int(age),)
+               out = 'Died at age ' +str(age)+newLine
+               out+=pU.table_header(['link','in'],newLine)
+               for row in run_query(s,t):
+                       link = pU.name_html([row[1],row[2]],newLine)
+                       year = pU.print_year(row[3])
+                       out+=pU.table_row([link,year],newLine)
+       else:
+               s = "SELECT diedYear, name,ID,bornYear,url"\
+                       +" FROM people"\
+                       +" WHERE diedYear = ?;"
+               out = 'Still alive'+newLine
+               out+=pU.table_header(['link','born in','wikipedia'],newLine)
+               for row in run_query(s,(presentYear,)):
+                       link = pU.name_html([row[1],row[2]],newLine)
+                       born = pU.print_year(row[3])
+                       if row[4]=='.':
+                               wlink = ''
+                       else:
+                               wlink = '<a href="'+row[4]+'">wikipedia</a>'
+                       out+=pU.table_row([link,born,wlink],newLine)
+       out+=pU.table_foot(newLine)
        return out
 
+
 def all_ancestors(personID,newLine):
-       #find parents
 
-       ancestors = [personID]
-       allAncestors = [personID]
-       trackLevel = [0]
-       level = 0
-
-       t = "SELECT name,id FROM people WHERE id=?"
-       id = (personID,)
-
-       out = "Ancestors of "
-       for row in run_query(t,id):
-               out += name_html(row,newLine)+newLine
-
-       while len(ancestors)>0:
-               level = level+1
-               newA =[]
-               thisout = "%s %s:%s" \
-               % (newLine,parent_level(level,'parent'),newLine)
-
-               for ancestor in ancestors:
-                       [parents, parentIDs,parentNames] \
-                               = find_parents(ancestor)
-                       for i in range(len(parents)):
-                               r = [parentNames[i],parentIDs[i]]
-                               thisout +=name_html(r,newLine)+newLine
-                               
-                               if r[1] not in allAncestors\
-                               and r[1]!=0:
-                                       newA.append(r[1])
-                                       allAncestors.append(r[1])
-                                       trackLevel.append(level)
-                               
-               ancestors = newA
-               out  +=thisout
 
+       s = "SELECT name,id FROM people WHERE id=?"
+       t = (personID,)
+       out=pU.print_tagged_query("Ancestors of ",s,t,newLine)
+
+       names = ['me']
+
+       allAncestors,levelDict = gQ.ancestors(int(personID))
+
+       for level in levelDict.keys():
+
+               out += eU.parent_level(level,'parent')+':'+newLine
+
+               for a in levelDict[level]:
+                       if eU.is_number(a):
+                               for r in run_query(s,(a,)):
+                                       out+=pU.name_html(r,newLine)+newLine
+                       else:
+                               out+=a+newLine
 
        image = "<img src = ancestorGraph.py?id=%s>" %personID
        out +=newLine + image+newLine
-       return [out, allAncestors,trackLevel]
 
+       return [out, allAncestors,levelDict]
+def all_descendants(personID,newLine):
+       s = "SELECT name,id,bornYear,diedYear FROM people WHERE id=?"
+       t = (personID,)
+       out = pU.print_tagged_query("Descendants of ",s,t,newLine)
+       names = ['me']
+       allDescendants,levelDict = gQ.descendants(int(personID))
+       for level in levelDict.keys():
+               out+=eU.parent_level(level,'child')+':'+newLine
+
+
+               out+=pU.table_header(['Name','Born','Died'],newLine)
+               for a in levelDict[level]:
+                       if eU.is_number(a):
+                               for r in run_query(s,(a,)):
+                                       n=pU.name_html(r,newLine)
+                                       b = r[2]
+                                       d = r[3]
+                       else:
+                               n=a
+                               b=0
+                               d=0
+                       if b==0:
+                               b = '?'
+                       if d==0:
+                               d = '?'
+                       out+=pU.table_row([n,b,d],newLine)
 
-def common_ancestors(IDA, IDB,newLine):
-       out = 'Common ancestors of:' + newLine
+               
+               out+=pU.table_foot(newLine)
 
-       s = "SELECT name,id FROM people WHERE id==?"
+       return [out, allDescendants,levelDict]
+def check_relationship(a,b):
+       s = 'SELECT related FROM marriages'\
+               +' WHERE ida =? AND idb=? AND related<>0'
+       t = (min(a,b),max(a,b))
+       for r in run_query(s,t):
+               return r[0]
 
+def update_relationship(a,b,r,commit):
+       s = 'SELECT related FROM marriages'\
+               +' WHERE ida =? AND idb=?'
+       t = (min(a,b),max(a,b))
 
-       names=[]
+       for row in run_query(s,t):
+               u = "UPDATE marriages SET Related = ?"\
+               +" WHERE ida = ? AND idb=?;"
+               v = (r,)+t
+               try:
+                       run_query(u,v)
+                       if commit==1:
+                               commit_changes()
+                       return 
+               except:
+                       return 
+
+
+def find_relationship(IDA,IDB,commit):
+       nameList=[]
+       s  = "SELECT name,id FROM people WHERE id ==?"
        for id in (IDA,IDB):
                t = (id,)
                for row in run_query(s,t):
-                       out += name_html(row,newLine)+newLine
-                       names.append(row[0])
-               if id==IDA:
-                       out += 'and'
-               out = out + newLine
-
-       if len(names)!=2:
-               related = 'No details held on one party'
-               out += related
-               return [out,[],related]
+                       nameList.append(pU.name_html(row,'<br>'))
+                               
        
+       mrca,orca,aL,bL = gQ.relationship(IDA,IDB)
+       related = eU.relationship(aL,bL,nameList)
+       update_relationship(IDA,IDB,related,commit)
+       return related 
 
-       a = all_ancestors(IDA,newLine)
-       b = all_ancestors(IDB,newLine)
+def relation_text(IDA,IDB,newLine):
        
-       ancestorsB = set(b[1])
-       ancestorsA = set(a[1])
-
-       common = ancestorsA.intersection(ancestorsB)
-       common = list(common)
+       IDA = int(IDA)
+       IDB = int(IDB)
+       related = check_relationship(IDA,IDB)
+       
+       if related is None:
+               related = find_relationship(IDA,IDB,1)
+               
+       
+       return related
+
+def common_ancestors(IDA,IDB,newLine):
+       related = relation_text(IDA,IDB,newLine)
+       out = related+newLine
+
+       if related[-11:]!='not related':        
+               mrca,orca,aL,bL = gQ.relationship(int(IDA),int(IDB))            
+               s = 'SELECT name,id FROM people WHERE id=?'
+               cText = 'Most recent common ancestors:'+newLine
+               for c in mrca:
+                       for row in run_query(s,(c,)):
+                               cText+=pU.name_html(row,newLine)+newLine
+               cText+=newLine
+               findName = re.compile('(<a.*?</a>) and (<a.*?</a>).*')
+               findNameP = re.compile('(<a.*?</a>) is (<a.*?</a>).*')
+               found = findName.search(related)
+               if found is None:
+                       found = findNameP.search(related)
+               nameA = found.group(1)
+               nameB = found.group(2)
+               cText+=nameA+"'s "+eU.parent_level(aL,'parent')\
+                       +newLine\
+                       +nameB+"'s "\
+                       +eU.parent_level(bL,'parent')
+
+
+               out += newLine+cText
+       
+               image = "<img src = jointAncestorGraph.py?id=%s&id2=%s&mL=%s>"\
+                       %(IDA,IDB,max(aL,bL))
 
+                       out +=newLine + image
+       out+=newLine
 
-       aLevels=[]
-       bLevels=[]
-       for c in common:
-               i = a[1].index(c)
-               aLevels.append(a[2][i])
-               i = b[1].index(c)
-               bLevels.append(b[2][i])
+        return out
 
-       s = "SELECT Name, ID, bornyear"\
-       +" FROM people"\
-       +" WHERE ID IN ("
-       for i in range(len(common)):
-               s += "?,"
-       if len(common)>0:
-               s = s[:-1]
-       s = s+") ORDER BY bornyear;"
+def list_territories(newLine):
+       s = "SELECT DISTINCT short"\
+       +" FROM styleDecomp"\
+       +" ORDER BY short;"
 
+       out = ''
+       terrs = []
+       for row in run_query(s,()):
+               match = 0
+               
+               for i in range(len(eU.maleStyles)):
+                       m = eU.maleStyles[i]+' '
+                       if re.search(m,row[0]):
+                               match = 1
+                               break
+               if match==1:
+                       t = row[0]
+               else:
+                       t = eU.swap_gender(row[0])                      
 
-       if len(common)==0:
-               related = '%s and %s are not related' %(names[0], names[1])
-               out = out + newLine + related
-               return [out, common,related]
+               if t not in terrs:
+                       terrs.append(t)
 
+       for i in range(len(terrs)):
+               terrs[i] = eU.make_plural(terrs[i])
+       
+       for terr in terrs:
+               out += pU.terr_html(terr,newLine,0,0) +newLine
 
-       out += print_tagged_query('',s,common,newLine)
+       return out
 
-       indexA=[]
-       indexB=[]
 
-       for i in range(len(common)):
-               if aLevels[i] == min(aLevels):
-                       indexA.append(i)
-               if bLevels[i] == min(bLevels):
-                       indexB.append(i)
+def list_families(newLine):
+       s = "SELECT family, count(*)"\
+       +" FROM families GROUP BY family ORDER BY family;"
+       out = pU.table_header(['family','members'],newLine)
        
+       for row in run_query(s,()):
+               link=pU.fam_html(row[0],newLine)
+               count = row[1]
+               out+=pU.table_row([link,count],newLine)
 
 
-       s = "SELECT name, id"\
-       +" FROM people"\
-       +" WHERE id=?"
+       out+=pU.table_foot(newLine)
+       return out
 
-       out  += '%sMost Recent Common Ancestors:%s' %(newLine,newLine)
-       mrca = []
-       for a in indexA:
-               t = (common[a],)
-               mrca.append(common[a])
-               out += print_tagged_query('',s,t,newLine)
-               if a!=indexA[-1]:
-                       out += 'and' + newLine
+def combine_states(aTerritory):
+       p = aTerritory
+       places = []
 
-       out += parent_level(aLevels[indexA[0]],'parent')
-       if len(indexA) >1:
-               out += 's'
+       predeccessorStates = eU.predeccessorStates
+       successorStates = eU.successorStates
+       
+       ap = eU.make_male(aTerritory)
+       while predeccessorStates.has_key(ap):
+               ap = predeccessorStates[ap][0]
+               places.append(ap)
+       
 
-       out +=' of %s%s'%( name_html([names[0],IDA],newLine),newLine)
+       ap = eU.make_male(aTerritory)
+       while successorStates.has_key(ap):
+               ap = successorStates[ap]
+               places.append(ap)
 
-       out += parent_level(bLevels[indexB[0]],'parent')
-       if len(indexB)>1:
-               out += 's'
-       out += ' of %s%s' %(name_html([names[1],IDB],newLine),newLine)
+       return places
 
+def people_in(fam,newLine):
+       s = 'SELECT name,people.id,bornYear,diedYear FROM'\
+       +' people INNER JOIN families'\
+       +' ON people.id = families.id'\
+       +' WHERE family = ? ORDER BY bornYear;'
+       t = (fam,)
 
-       al = aLevels[indexA[0]]
-       bl = bLevels[indexB[0]]
+       out='Family: %s' %fam
+       out+=newLine+newLine
 
-       related = relationship(al,bl,names)
-       out +=newLine + related
+       out += pU.table_header(['id','name','born','died'],newLine)
+       ids=''
+       for row in run_query(s,t):
+               name=pU.name_html(row,newLine)
+               
+               b = row[2]
+               d = row[3]
+               if b==0:
+                       b='?'
+               if d==0:
+                       d = '?'
+               if d==presentYear:
+                       d='present'
+               out+=pU.table_row([row[1],name,b,d],newLine)
+               ids+='%d,' % row[1]
+       ids=ids[:-1]
+       out+=pU.table_foot(newLine)
+
+       image = "<img src = rulersGraph.py?names=%s>"\
+               % ids
+       out+=image
+       return out
 
 
-       image = "<img src = jointAncestorGraph.py?id="+str(IDA)\
-               +"&id2="+str(IDB) + "&LA=" + str(min(aLevels)) \
-               +"&LB=" + str(min(bLevels))+">"
+def rulers_of(aTerritory,newLine):
+       
+       out = pU.terr_html(eU.make_male(aTerritory),newLine,0,0)+newLine
+       
+       otherStates = combine_states(aTerritory)
+       if len(otherStates)>0:
+               out+="Otherwise:"+newLine
+       for s in otherStates:
+               out+=pU.terr_html(s,newLine,0,0)+newLine
 
-       image = "<img src = jointAncestorGraph.py?id=%s&id2=%s&LA=%d&LB=%d>"\
-               %(IDA,IDB,min(aLevels),min(bLevels))
+       out += find_rulers(aTerritory,newLine)[0]
 
 
-        out +=newLine + image+newLine
+       image = "<img src = rulersGraph.py?terr=%s>" \
+               %(re.sub(' ','%20',aTerritory))
+       out+=image
+       return out
 
-       return [out,common,related]
+def find_rulers(aTerritory,newLine):
+       places = [eU.make_singular(aTerritory)]
+       places+=combine_states(aTerritory)
 
-def relationship(level1, level2,names):
+       out = ''
+       fullTerr = []
 
-       if level1==0 and level2==0:
-               return "%s is %s" %(names[0],names[1])
-       if level1==0:
-               return "%s is %s's %s" \
-                       %(names[0],names[1],parent_level(level2,'parent'))
+       for p in places:
+               s = "SELECT DISTINCT short"\
+                       +" FROM styleDecomp"\
+                       +" WHERE short LIKE ?"\
+                       +" OR short LIKE ?"\
+                       +" OR short LIKE?;"
+               t = ('%'+p+'%','%'+eU.swap_gender(p)+'%',\
+               '%'+eU.make_plural(p)+'%')
 
-       if level2==0:
-               return "%s is %s's %s" \
-                       %(names[1],names[0],parent_level(level1,'parent'))
 
+               for row in run_query(s,t):
+                       fullTerr.append(row[0])
 
-       if level1>=level2:
-               remove = level1-level2
-               cousinNum = level2-1
-       else:
-               remove = level2-level1
-               cousinNum = level1-1
-
-       if cousinNum==0:
-               uaLevel =  parent_level(remove,'uncle or aunt')
-               if level1<= level2:
-                       return "%s is %s's %s" % (names[0],names[1],uaLevel)
-
-               if level2<level1:
-                       return "%s is %s's %s" % (names[1],names[0],uaLevel)
-
-       c=ordinal_numbers(cousinNum)
-       if remove == 1:
-               rem = 'once'
-       elif remove ==2:
-               rem = 'twice'
-       else:
-               rem = str(remove) + ' times'            
-
-       r = "%s and %s are %s cousins" % (names[0],names[1],c)
-       if remove !=0:
-               r += ' %s removed' % rem
-
-       return r
-
-def parent_level(level,type):
-       if level == 0:
-               if type=='parent':
-                       return 'self'
-               else:           
-                       return 'sibling'
-       out = type
-       if level ==1:
-               return out
-       if type =='parent':
-               out = 'grand ' + out
-       else:
-               out = 'great '+out
-       if level ==2:
-               return out
-       for i in range(2,level):
-               out = 'great '+out
-       return out
 
-def rulers_of(aTerritory,newLine):
+       if len(fullTerr)==0:
+               return out,[]
+               
+       tq = "SELECT styleDecomp.style,name,people.ID,"\
+               +" startyear,stopyear,short"\
+               +" FROM styleDecomp INNER JOIN styles"\
+               +" ON styleDecomp.style = styles.style"\
+               +" INNER JOIN people"\
+               +" ON people.ID = styles.ID"\
+               +" WHERE short IN ("
+
+       for i in range(len(fullTerr)):
+               tq+='?,'
+       tq = tq[:-1]    
+       tq+=" )ORDER BY startyear,stopyear;"
+       s = ''
+
+       t = tuple(fullTerr)
+       rulers = []
+       out+=pU.table_header(['link','style','from', 'to','house'],newLine)
+       for row in run_query(tq,t):
+               #if row[0]!=s:
+               #       out +=newLine+row[0]+newLine
+               #       s = row[0]
+               fy = pU.print_year(row[3])
+               ft = pU.print_year(row[4])
+               
 
-       tq = "SELECT name, people.ID, startyear,stopyear,territory"\
-               +" FROM territories INNER JOIN people"\
-               +" ON people.ID = territories.ID"\
-               +" WHERE territory LIKE ?"\
-               +" ORDER BY territory,startyear,stopyear;"
+               id = row[2];
+               u = "SELECT family FROM families WHERE id = ?"
+               v = (id,)
+               house = ''
+               for r in run_query(u,v):
+                       house+=pU.fam_html(r[0],newLine)
 
+               out+=pU.table_row([pU.name_html(row[1:],newLine),\
+                       row[0],fy,ft,house],newLine)
+               
+               if row[2] not in rulers:
+#                      rulers.append(row[2])
+                       rulers = [row[2]]+rulers
+       out+=pU.table_foot(newLine)
+       return [out,rulers]
+
+def find_adjacent(terr,start,stop,id):
+       s = "SELECT name,people.id,stopyear"\
+       +" FROM people INNER JOIN styles"\
+       +" ON people.id = styles.id"\
+       +" INNER JOIN styleDecomp"\
+       +" ON styles.style = styleDecomp.style"\
+       +" WHERE short = ? AND stopyear<=? AND stopyear <>0 AND people.id<>?"\
+       +" ORDER BY stopyear DESC, startyear DESC;"
 
 
-       thisT  = ''
-       last = ''
-       out = ''
-       for row in run_query(tq,(aTerritory+'%',)):
-               if row[4]!=last and last!='':
-                       out += 'Rulers of %s:%s%s%s'\
-                       %(terr_html(last,newLine,0,0),newLine,thisT,newLine)
-                       thisT = ''
+       t = (terr,start,id)
+       myPrevious=[]
+       y=0
+       for row in run_query(s,t):
+               myPrevious = row[0:2]
+               y = row[2]
+               break
+
+       t = (eU.swap_gender(terr),start,id)
+       for row in run_query(s,t):
+               if row[2]>y:
+                       myPrevious = row[0:2]
+               break
+
+       u = "SELECT name,people.id,startyear"\
+        +" FROM people INNER JOIN styles"\
+       +" ON people.id = styles.id"\
+               +" INNER JOIN styleDecomp"\
+        +" ON styles.style = styleDecomp.style"\
+        +" WHERE short = ? AND startyear>=? AND startyear <>0 AND people.id<>?"\
+        +" ORDER BY startyear;"
+               
+       v = (terr,stop,id)
+       myNext=[]
+       y=float('inf')
+        for r in run_query(u,v):
+               myNext = r[0:2]
+               y = r[2]
+                break
+
 
-               thisT += "%s from %s to %s%s" \
-               % (name_html(row,newLine),row[2],row[3],newLine)
-               last = row[4]
+       v = (eU.swap_gender(terr),stop,id)
+       for r in run_query(u,v):
+               if r[2]<y:
+                       myNext = r[0:2]
+               break
 
-       out += 'Rulers of %s:%s%s' \
-       % (terr_html(row[4],newLine,0,0),newLine,thisT)
+       return [myPrevious, myNext]
 
-       return out      
 
 def find_person(ID):
-        s = "SELECT name || ','||ID, name, ID FROM people WHERE ID=?"
+        s = "SELECT name||','||ID, name, ID FROM people WHERE ID=?"
         t = (ID,)
 
         for row in run_query(s,t):
@@ -805,19 +1503,7 @@ def find_person(ID):
                selfName = row[1]
                selfID = row[2]
                 return [Self, selfID,selfName]
-def isKing(ID):
-       ID = int(ID.split(',')[-1])
-       s=  "SELECT style FROM styles WHERE ID=?"
-       t = (ID,)       
 
-       k = 0
-       spellingsOfKing = ['King','Queen','king','queen']
-       for row in run_query(s,t):
-               for s in spellingsOfKing:
-                       if re.match('.*'+s,row[0]) != None:
-                               k = 1
-
-       return k
 
 def find_parents(ID):
         s = "SELECT name, parentID"\
@@ -833,7 +1519,7 @@ def find_parents(ID):
         for row in run_query(s,t):
                 if row[0]!=None:
                         p = row[0] + ',' + str(row[1])
-                        pID = row[1]
+                        pID = int(row[1])
                        pN = row[0]
                 else:
                         p = row[1] + ',p' + str(ID)
@@ -843,41 +1529,79 @@ def find_parents(ID):
                 parentIDs.append(pID)
                parentNames.append(pN)
 
-       if parents[1]==parents[0]:
+       if len(parents)>1 and parents[1]==parents[0]:
                parents[1] = parents[1] + ' 2'
 
         return [parents,parentIDs,parentNames]
 
+
+
+def is_married(IDa, IDb):
+       
+       s = "SELECT idb FROM marriages WHERE ida =?;"
+       t = (min(IDa,IDb),)
+
+               
+       for row in run_query(s,t):
+               if int(row[0])==max(IDa,IDb):
+                       return 1
+       return 0        
+
 def find_spouses(ID):
         t = (ID,)
 
-        order = [["IDb","IDa"],["IDa","IDb"]]
 
         spouses = []
         spousesID=[]
        spousesNames=[]
-        for o in order:
-                s = "SELECT name, marriages." + o[0]\
-                +" FROM marriages LEFT JOIN people"\
-                +" ON marriages." +o[0]+" = people.ID"\
-                +" WHERE marriages."+o[1]+" = ?;"
-
-
-                for row in run_query(s,t):
-                        if row[0]!=None:
-                                s = row[0] + "," +str(row[1])
-                                sID = row[1]
-                                       sN = row[0]
-                       elif row[1] !='':
-                                s=row[1] + ",s" +str(ID)
-                                sID = 0
+       spouseDates = []
+
+       s = "SELECT ida,a.name,idb,b.name,marriage,end,"\
+       +" a.bornYear,a.diedYear,b.bornYear,b.diedYear,marriageYear,"\
+       +" a.diedMonth,a.diedDay,b.diedMonth,b.diedDay"\
+       +" FROM marriages"\
+       +" LEFT JOIN people AS a"\
+       +" ON ida = a.ID"\
+       +" LEFT JOIN people AS b"\
+       +" ON idb = b.ID"\
+       +" WHERE ida = ? OR idb = ?"\
+       +" ORDER BY marriageYear;"\
+
+       t = (ID,ID)
+       for row in run_query(s,t):
+               sID = ''
+               if row[0]!=int(ID): #spouse is ida
+                       if row[1]!=None:
+                               s = row[1]+","+str(row[0])
+                               sID = row[0]
                                sN = row[1]
-                        if row[1] !='':
-                                spouses.append(s)
-                                spousesID.append(sID)
-                               spousesNames.append(sN)
-
-        return [spouses,spousesID,spousesNames]
+                       elif row[0]!='':
+                               s = row[0]+",s"+str(ID)
+                               sID = 0
+                               sN = row[0]
+                       myDates = [row[1],row[0],row[4],row[5],row[6],\
+                       row[7],row[11],row[12]]
+               else: #spouse is idb
+                       if row[3]!=None:
+                               s = row[3]+","+str(row[2])
+                               sID = row[2]
+                               sN = row[3]
+                       elif row[2]!='':
+                               s = row[2]+",s"+str(ID)
+                               sID = 0
+                               sN=  row[2]     
+                       myDates = [row[3],row[2],row[4],row[5],row[8],row[9],\
+                               row[13],row[14]]
+                       for i in range(len(myDates)):
+                               if myDates[i] is None:
+                                       myDates[i]=0
+               if sID!='':
+                       spouses.append(s)
+                       spousesID.append(sID)
+                       spousesNames.append(sN)
+                       spouseDates.append(myDates)
+
+        return [spouses,spousesID,spousesNames,spouseDates]
        
 
 def find_children(ID):
@@ -887,11 +1611,11 @@ def find_children(ID):
                 +" ON p1.ID = p2.ID"\
                 +" INNER JOIN parents p3"\
                 +" ON p1.ID = p3.ID"\
-                +" LEFT JOIN people"\
-                +" p4 ON p3.parentID = p4.ID"\
+                +" LEFT JOIN people p4"\
+                +" ON p3.parentID = p4.ID"\
                 +" WHERE p2.parentID = ?"\
                 +" AND p3.parentID<>?"\
-                +" ORDER BY p1.bornYear;"
+                +" ORDER BY p1.bornYear,p1.ID;"
 
         t = (ID,ID)
 
@@ -933,26 +1657,65 @@ def person_info(personID,newLine):
 
        mainDiv = ''    
        #Id, Name, Dates, Style, Style-Dates
-       s = "SELECT * FROM people WHERE ID = ?"
+       s = "SELECT id,name,fullname,url,picture,Born,Died,"\
+               +" bornYear,diedYear,diedMonth,diedDay"\
+               +" FROM people WHERE ID = ?"
+       rows = 0
        for row in run_query(s,t):
+               rows = 1
                mainDiv += startP
-               mainDiv += 'ID: %s%s' %(row[0] ,newLine)
-               mainDiv += print_tagged_name('Name',[row[1], row[0]]\
+               preURL = pU.name_html(['previous',row[0]-1],newLine)
+               postURL =  pU.name_html(['next',row[0]+1],newLine)
+               mainDiv += 'ID: %s(%s %s)%s' %(row[0],preURL,postURL ,newLine)
+               mainDiv += pU.print_tagged_name('Name',[row[1], row[0]]\
                        ,newLine)
+               mainDiv+='Full Name: '+row[2]+newLine
                mainDiv +=endP
+
                name = row[1]
-               url = row[9]
-               picture = row[10]
+               fullname = row[2]
+               url = row[3]
+               picture = row[4]
+               born = row[5]
+               died = row[6]
+               bornYear = row[7]
+               diedYear = row[8]
+               diedMonth = row[9]
+               diedDay = row[10]
 
                mainDiv += startP
-               mainDiv += '%sBorn:%s%s '% (newLine,row[3],newLine)
-               bornYear = row[4]
-               mainDiv +='Died: %s' % row[5]
+               mainDiv += '%sBorn:%s%s '% (newLine,born,newLine)
+
+
+
+               if died!='present':
+                       mainDiv +='Died: %s' % died
+       
+                       if diedYear != 0 and bornYear !=0:
+
+                               u = "SELECT age FROM"+ageTable\
+                                       +" WHERE id = ?"
+                               
+                               for row in run_query(u,t):
+                                       mainDiv += ", aged %s" %(row[0])
+               else:
+                       u = "SELECT age FROM" + ageNowTable\
+                               +" WHERE id = ?"
+
+                       for row in run_query(u,t):
+                               mainDiv +='Still Alive, aged %s' %(row[0])
+
+                       
 
-               if row[6] != 0 and row[4] !=0:
-                       mainDiv += ", aged %s" %(row[6]-row[4])
                mainDiv +=endP
 
+       s = 'SELECT family FROM families WHERE ID = ?'
+       
+       for row in run_query(s,t):
+               mainDiv+='Family: %s' % pU.fam_html(row[0],newLine)
+
+       if rows==0:
+               return ''
 
        s = "SELECT * FROM styles WHERE ID = ?"
        for row in run_query(s,t):
@@ -961,16 +1724,19 @@ def person_info(personID,newLine):
 
                mainDiv += 'Territories:%s' % newLine
 
-               u = "SELECT * FROM territories"\
-               +"  WHERE ID =? AND startYear =? AND stopYear=?"
-               v=(personID,row[3],row[5])
+               w = "SELECT short FROM styleDecomp"\
+               +" WHERE style = ?"
 
-               any = 0
-               for r in run_query(u,v):
-                       mainDiv += terr_html(r[1],newLine,r[3],r[5]) +','
-                       any = 1
-               if any ==1:
-                       mainDiv = mainDiv[:-1] + newLine
+               for r in run_query(w,(row[1],)):
+                       [p,n]=find_adjacent(r[0],row[3],row[5],personID)
+                       if len(p)>0:
+                               mainDiv +='%s|'%(pU.name_html(p,newLine))
+
+                       mainDiv+=pU.terr_html(r[0],newLine,row[3],row[5])
+
+                       if len(n)>0:
+                               mainDiv+='|%s'%(pU.name_html(n,newLine))
+                       mainDiv+=newLine
 
                mainDiv +=  'From: '+row[2] + newLine
                 mainDiv +=  'To: '+row[4]      
@@ -981,13 +1747,6 @@ def person_info(personID,newLine):
 
 
        mainDiv += startP
-       s = "SELECT people.Name,consort "\
-               +"FROM consorts LEFT JOIN people"\
-               +" ON people.ID = consorts.consort"\
-               +" WHERE consorts.ID = ?"
-       for row in run_query(s,t):
-               mainDiv += print_tagged_name\
-               ('Consort of',row,newLine)
        mainDiv += endP
 
        #find parents
@@ -996,22 +1755,118 @@ def person_info(personID,newLine):
        mainDiv += startP
        for i in range(len(parents)):
                r = [parentNames[i],parentIDs[i]]
-               mainDiv += print_tagged_name('Parent',r,newLine)
+               mainDiv += pU.print_tagged_name('Parent',r,newLine)
        mainDiv += endP
 
        #find spouses
 
-       [spouses,spousesID,spousesNames] = find_spouses(personID)
+       [spouses,spousesID,spousesNames,spouseDates] = find_spouses(personID)
 
        mainDiv += startP
 
        for i in range(len(spouses)):
                r = [spousesNames[i],spousesID[i]]
-               mainDiv += print_tagged_name('Spouse',r,newLine)
-               mainDiv += \
-               relationship_html(personID,r[1],newLine)
+               d = spouseDates[i][2:8]
+
+               mainDiv += pU.print_tagged_name('Spouse',r,newLine)
+               if d[0]!='.':
+                       mainDiv+='married: '+d[0]+newLine
+               else:
+                       mainDiv+='marriage dates not yet recorded'\
+                       + newLine
+               if d[1]!='.':
+                       mainDiv+='marriage ended: '+d[1]+newLine
+               elif d[0]!='.':
+                       dPrint = 1
+                       if d[3]<diedYear:
+                               y = pU.print_year(d[3])
+                               
+                               ot = 'their'
+                       elif d[3]==diedYear and diedYear!=presentYear:
+                               y = d[3]
+                               
+                               if d[4]<diedMonth:
+                                       ot = 'their'
+                               elif d[4]>diedMonth:
+                                       ot = 'own'
+                               else:
+                                       if d[5]<diedDay:
+                                               ot = 'their'
+                                       elif d[5]>diedDay:
+                                               ot = 'own'
+                                       else:
+                                               dPrint = 0
+                                               mainDiv+='until both of their deaths in %s%s'\
+                                                       %(str(y),newLine)
+
+                       else:
+                               if diedYear==presentYear:
+                                       dPrint = 0
+                                       mainDiv+='still married%s'%(newLine)
+                               else:
+                                       y = str(pU.print_year(diedYear))
+                                       
+                                       ot='own'
+                       if dPrint==1:
+                               mainDiv+='until %s death in %s%s' %(ot,y,newLine)
+
+               if r[1]!=0:
+                       mainDiv +=''
+                       #mainDiv += \
+                       #       pU.relationship_html(personID,r[1],newLine)\
+                       #       +newLine
+               else:
+                       mainDiv+=newLine
+
+               marriageStyles = ''
+               mStart = int(findYear.find_year(d[0]))
+               mStop = int(findYear.find_year(d[1]))
+               if mStop == 0:
+                       mStop = diedYear
+
+               if mStart==0:
+                       continue
+
+
+               ss = "SELECT styles.style, short,startyear,"\
+               +" stopyear"\
+               +" FROM styles INNER JOIN styledecomp"\
+               +" ON styles.style = styledecomp.style"\
+               +" WHERE  id = ?;"
+               st = (spousesID[i],)
+
+               for sr in run_query(ss,st):
+                       starty = int(sr[2])
+                       stopy = int(sr[3])
+                       
+                       if mStart>stopy:
+                               continue
+                       if mStop<starty and mStop != 0:
+                               continue
 
-       mainDiv  = mainDiv + endP
+
+                       if mStart>starty:
+                               fromy = mStart
+                       else:
+                               fromy = starty
+
+                       if mStop<stopy and mStop !=0:
+                               to = str(mStop)
+                       elif diedYear<=stopy:
+                               to = str(pU.print_year(diedYear))
+                               
+                       else:
+                               to = str(sr[3])
+
+
+                       marriageStyles+='%d to %s: %s%s' \
+                       %(fromy, to,eU.swap_gender(sr[1]),newLine)
+
+               if len(marriageStyles)>0:
+                       mainDiv+="Through this marriage:"+newLine
+                       mainDiv+=marriageStyles+newLine
+
+       mainDiv  = mainDiv + newLine+endP
 
        #find children
        [nodes,IDs,names,childrenBorn] = \
@@ -1020,30 +1875,35 @@ def person_info(personID,newLine):
        top = ''
        for i in range(len(nodes)):
                cr = [names[i][0],IDs[i][0]]
-               thisChild = print_tagged_name('Child',cr,newLine)
+               thisChild = pU.print_tagged_name('Child',cr,newLine)
 
                opr=[names[i][1],IDs[i][1]]
                top = names[i][1]
                if i==0 or  top != names[i-1][1]:
                        mainDiv +=endP
                        mainDiv += startP
-                       mainDiv += print_tagged_name\
+                       mainDiv += pU.print_tagged_name\
                         ('With',opr, newLine)
 
 
                #age when child born
                cb = childrenBorn[i]
                if  cb!=0 and  bornYear != 0:
-                       age = cb-bornYear
-                       thisChild = thisChild[:-4] + \
-                               " at the age of "+str(age) + newLine
+
+                       cs = "SELECT age,pID,cID FROM "+ageChildTable\
+                               +"WHERE pID=? AND cID =?"
+                       ct = (personID,IDs[i][0])
+
+                       for row in run_query(cs,ct):
+                               thisChild = thisChild[:-4]+\
+                               " at the age of "+str(row[0]) +newLine
                mainDiv += thisChild
        
        mainDiv += endP
 
 
        if newLine == '<br>':
-               output = '<div id = "main" style = " float:left">';
+               output = '<div id = "main" style = " float:left;width:75%">';
                output += mainDiv +  "</div>"
 
                output += "<div id = 'image' "\
@@ -1146,11 +2006,14 @@ def connect():
        global conn
        conn = sqlite3.connect\
                ('/home/naath/familyTreeProject/familyTree/tree.db')
-       return conn
+       conn.cursor().execute('PRAGMA journal_mode = WAL')
 
 def make_cursor():
        return conn.cursor()
+
+def commit_changes():
+       conn.commit()
        
-def close(conn):
+def close():
        conn.close