Ejemplo n.º 1
0
def groupByMessage(als:Iterable[models.Alert]) \
    -> Iterable[Tuple[models.Message,List[str]]]:
    """ Group the alerts by message. For each group of alerts with
    a messages, return that message and the userIds of the users who 
    starred it.
    """
    mid: str = ""  # message id
    m = None  # message of (mid)
    users: List[str] = []
    dpr("mid=%r users=%r", mid, users)
    for al in als:
        newMid = al.message_id
        if newMid != mid:
            dpr("mid=%r newMid=%r", mid, newMid)
            if mid != "":
                dpr("yielding (%r, %r)", mid, users)
                yield (m, users)
            mid = newMid
            m = models.Message.getDoc(mid)
            users = []
        users += [al.doer_id]
        dpr("mid=%r users=%r", mid, users)
    #//for al
    if mid != "":
        dpr("yielding (%r, %r)", mid, users)
        yield (m, users)
Ejemplo n.º 2
0
def user(id):
    if id=='NEW':
        doc = userdb.User()
        dpr("doc=%r", doc)
    else:
        doc = userdb.User.getDoc(id)
        dpr("doc=%r", doc)
    msg = ""

    if request.method=='POST':
        doc = doc.populateFromRequest(request)
        if doc.isValid():
            if request.form['delete']=="1":
                doc.delete()
                msg = "Deleted user"
            else:    
                doc.save()
                msg = "Saved user"
    #//if

    tem = jinjaEnv.get_template("user.html")
    h = tem.render(
        doc = doc,
        id = htmlEsc(id),
        msg = ht.goodMessageBox(msg),
    )
    return h


#---------------------------------------------------------------------


#end
Ejemplo n.º 3
0
def xFollow(id: str, status: str):
    """
    @param id = the followee user who the currently-logged-in user
        is following or unfollowing
    @param status = following status, 0=unfollow, 1=follow
    """
    makeFollowing = (status == "1")
    cun = currentUserName()
    dpr("id=%r status=%r cun=%r", id, status, cun)
    if not cun: return "{}"

    cu = User.getDoc(cun)
    if not cu: return "{}"
    followee = User.getDoc(id)
    if not followee: return "{}"

    ai = models.getAccountInfo(cun)
    followingSet = set(ai.following_ids)
    if makeFollowing:
        followingSet2 = followingSet | set([id])
    else:
        followingSet2 = followingSet - set([id])
    if followingSet2 != followingSet:
        ai.following_ids = list(followingSet2)
        ai.save()
    return "{}"
Ejemplo n.º 4
0
def adq(qtext: str, id: str = ""):
    global qList
    if id:
        dpr("id=%r", id)
        id = questionManager.getCurrentGroupId() + "-" + id
        dpr("id=%r", id)
    q = AgreeDisagreeQuestion(id, qtext)
    questionManager.addQuestion(q)
Ejemplo n.º 5
0
def wiki_page(u, pathName):
    dpr("pathName=%r", pathName)
    folder, filename = decomposePathName(pathName)
    dpr("folder=%r filename=%r", folder, filename)
    if filename == "":
        return wikiDir(u, folder)
    else:
        return wikiPage(u, folder, filename)
Ejemplo n.º 6
0
def mcq(qtext: str, answers: MultiChoiceAnswers, id: str = ""):
    global qList
    if id:
        dpr("id=%r", id)
        id = questionManager.getCurrentGroupId() + "-" + id
        dpr("id=%r", id)
    q = MultiChoiceQuestion(id, qtext, answers)
    questionManager.addQuestion(q)
Ejemplo n.º 7
0
def hashPassword(password: str) -> str:
    encrypted = pyscrypt.hash(password=toBytes(password),
                              salt=toBytes("salt"),
                              N=128,
                              r=1,
                              p=1,
                              dkLen=256)
    dpr("encrypted=%r:%s", encrypted, type(encrypted))
    hx = toHex(encrypted)
    dpr("hx=%r:%s", hx, type(hx))
    return hx
Ejemplo n.º 8
0
def askq():
    dpr("in askq()")
    if request.method == 'POST':
        pass
    #//if

    tem = jinjaEnv.get_template("askq.html")
    h = tem.render(
        qs=questlib.questionListH()  # get html-formatted list of questions
    )
    return h
Ejemplo n.º 9
0
def calcGroupTable(userName: str) -> str:
    """ caslculate the group table for the current user.
    Returns html.
    """
    h = """<table class='bz-report-table'>
<tr>
    <th>Group</th>
    <th>Questions<br>Answered</th>
    <th>Questions<br>Unanswered</th>
    <th>Details</th>
</tr>    
"""
    groups = questionManager.getGroups()
    for group in groups:
        dpr("group.id=%r", group.id)
        numQs = len(group.questions)
        numAnswered = len(answeredQs(currentUserName(), group.questions))
        numUnanswered = numQs - numAnswered
        if numUnanswered == 0:
            detailsH = form(
                "View <a href='/results/{groupId}' class='green'>"
                "<i class='fa fa-star'></i> "
                "Your Results</a>",
                groupId=htmlEsc(group.id))
        else:
            detailsH = ("<i class='fa fa-lock'></i> "
                        "<i>answer all questions to unlock details</i>")
        h += form(
            """
<tr>
    <td><a href="/group/{groupId}">{groupName}</a></td>
    <td style='text-align:right;'>
        <a href="/answered/{groupId}">{numAnswered}</a></td>
    <td style='text-align:right;'>
        <a href="/ask/{groupId}">{numUnanswered}</a>/{numTotal}</td>
    <td>{details}</td>
</tr>            
""",
            groupId=htmlEsc(group.id),
            numQs=numQs,
            groupName=htmlEsc(group.title),
            numAnswered=numAnswered,
            numUnanswered=numUnanswered,
            numTotal=numQs,
            details=detailsH,
        )
    #//for
    h += "</table>\n"
    return h
Ejemplo n.º 10
0
def pollChartData() -> dict:
    """ return data for poll chart, in format for Flot charting
    application
    """
    # polls, sorted earliest first
    allPolls = sorted(Poll.polls, key=lambda po: po.dateInt)
    j = []
    partyStrengths = []
    for p, xAdj in zip(POLL_PARTIES, PARTY_X_ADJ):
        pa = party.Party.docs[p]
        xySeries = []
        dataForTrend = []
        trendSeries = []
        for po in allPolls:
            xySeries.append([po.dateInt+xAdj, po.__dict__[p]])
            dataForTrend.append(
                (po.dateInt, po.sample, po.__dict__[p]))
            trendSeries.append([po.dateInt, calcTrend(dataForTrend)])
        #//for po 
        series = {
            'label': p,
            'color': pa.col,
            'data': xySeries,
            'points': {'show': True}
        }    
        trendSeries = {
            'color': pa.col,
            'data': removeDuplicateDates(trendSeries),
            'lines': {'show': True, 'lineWidth': 2}
        }    
        j.append(series)
        j.append(trendSeries)
        j.append({
            'data': [[0,0]],
            #'points': {'show': True}
        })    
        partyStrengths.append({
            'name': pa.getNameH(),    
            'color': pa.col,
            'strength': trendSeries['data'][-1][1]
        })    
    #//for pa   
    j.append({
        'data': [[0,0]],
        #'points': {'show': True}
    })  
    dpr("partyStrengths=%r", partyStrengths)
    return j, partyStrengths
Ejemplo n.º 11
0
def blog(id):
    user = User.getDoc(id)
    ai = models.getAccountInfo(id)
    lf = BlogFormatter(id)
    numPosts = models.Message.count({'author_id': id})
    numHeadPosts = models.Message.count({
        'author_id': id,
        'replyTo_id': {
            '$in': [None, '']
        },
    })
    numFollowing = len(ai.following_ids)
    numFollowers = models.AccountInfo.count({'following_ids': id})

    cun = currentUserName()
    if not cun:
        # not logged in, so no follow button
        followButton = ""
    else:
        if models.follows(cun, id):
            # follows, so unfollow button
            followButton = "unfollow"
        else:
            # doesn't currently follow, so follow button
            followButton = "follow"
    dpr("followButton=%r", followButton)

    tem = jinjaEnv.get_template("blog.html")
    h = tem.render(
        id=id,
        idJson=json.dumps(id),
        user=user,
        ai=ai,
        blogTitle=ai.asReadableH('title'),
        name=ai.asReadableH('realName'),
        bio=ai.bioHtml,
        numPosts=numPosts,
        numHeadPosts=numHeadPosts,
        numFollowing=numFollowing,
        numFollowers=numFollowers,
        followButton=followButton,
        lf=lf,
    )
    return h
Ejemplo n.º 12
0
def login():
    tem = jinjaEnv.get_template("login.html")
    doc = LoginForm()
    msg = ""

    if request.method=='POST':

        #>>>>> CSRF handling
        dpr("@@@ session=%r @@@", session)
        token = session.pop('_csrf_token', None)
        dpr("@@@ token=%r @@@", token)
        #if not token or token != request.form.get('_csrf_token'):
        #    pass
        #    #abort(403)

        doc = doc.populateFromRequest(request)
        u = userdb.User.find_one({'userName': doc.userName})

        ok = u and userdb.verifyPassword(u.hashedPassword,
                                         doc.password)
        dpr("doc.password=%r ok=%r", doc.password, ok)
        if ok:
            login_user(u)
            return redirect("/", code=302)
        else:
            msg = "login failed"

    h = tem.render(
        doc = doc,
        msg = ht.errorBox(msg),
    )
    return h
Ejemplo n.º 13
0
def ask(groupId, numQs=DEFAULT_NUM_QS):
    numQs = butil.exValue(lambda: int(numQs), DEFAULT_NUM_QS)
    dpr("groupId=%r, numQs=%r", groupId, numQs)
    group = questionManager.getGroup(groupId)
    if not group:
        return http403("Group does not exist")

    cun = currentUserName()

    if request.method == 'POST':
        rf = dict(request.form)
        dpr("request form data: rf=%r", rf)
        # in (rf) keys are question ids, values are question values.
        # if the user hasn't answered a question, it is missing from the
        # dictionary
        for qid, ansVal in rf.items():
            q = getQ(group.questions, qid)
            if q:
                models.saveAnswer(cun, q.qid, ansVal)
        #//for
    #//if

    unansweredQs = getUnansweredQs(group, cun)
    qsToAsk = unansweredQs[:numQs]
    qListH = getQuestionsH(qsToAsk)
    numAns = len(group.questions) - len(unansweredQs)

    tem = jinjaEnv.get_template("ask.html")
    h = tem.render(
        group=group,
        groupTitle=htmlEsc(group.title),
        groupId=htmlEsc(group.id),
        numQ=len(group.questions),  # questions in this group
        numAns=numAns,  # q's answered
        numUnanswered=len(unansweredQs),  # q's unanswered
        numAsk=len(qsToAsk),  # q's to ask on this page
        qs=qListH,
    )
    return h
Ejemplo n.º 14
0
def accountSettings():
    cun = currentUserName()
    dpr("id=%r cun=%r", id, cun)
    #if id != cun:
    #    return http403()
    user = User.getDoc(cun)
    ai = models.getAccountInfo(cun)
    msg = ""
        
    if request.method=='POST':
        ai = ai.populateFromRequest(request)
        ai.save()
        msg = "Saved account settings"
    #//if    
    
    tem = jinjaEnv.get_template("accountSettings.html")
    h = tem.render(
        user = user,
        ai = ai,
        msg = ht.goodMessageBox(msg),
    )
    return h
Ejemplo n.º 15
0
 def substFun(self, mo) -> str:
     """ Substitution function
     """
     dpr("substFun() mo.groups()=%r start=%r end=%r", mo.groups(),
         mo.start(), mo.end())
     matchedText = mo.string[mo.start():mo.end()]
     if matchedText[:2] == "[#":
         hashtag = matchedText[2:-1]
     else:
         hashtag = matchedText[1:]
     dpr("matchedText=%r hashtag=%r", matchedText, hashtag)
     canonicalTag = hashtag.lower().replace("-", "_").replace(" ", "_")
     dpr("canonicalTag=%r", canonicalTag)
     self.tagSet.add(canonicalTag)
     dpr("self.tagSet=%r", self.tagSet)
     result = "<a class='tag' href='/tag/%s'>#%s</a>" % (canonicalTag,
                                                         hashtag)
     return result
Ejemplo n.º 16
0
def verifyPassword(hashedPassword, guessedPassword):
    encrypted = pyscrypt.hash(password=toBytes(guessedPassword),
                              salt=toBytes("salt"),
                              N=128,
                              r=1,
                              p=1,
                              dkLen=256)
    dpr("encrypted=%r:%s", encrypted, type(encrypted))
    hx = toHex(encrypted)
    dpr("hx=%r:%s", hx, type(hx))
    ok = (hx == hashedPassword)
    dpr("hashedPassword=%r ok=%r", hashedPassword, ok)
    return ok
Ejemplo n.º 17
0
def getArticles():
    articleFns = butil.getFilenames(ARTICLE_DIR, "*.md")
    dpr("ARTICLE_DIR=%r", ARTICLE_DIR)
    dpr("articleFns=%r", articleFns)
    h = ""
    for afn in articleFns:
        title = getTitle(butil.join(ARTICLE_DIR, afn))
        dpr("afn=%r title=%r", afn, title)
        h += form(
            "<p><a href='/article/{art}'>"
            "<i class='fa fa-file-text-o'></i> {title}</a></p>\n",
            art=afn[:-3],
            title=title)
    #//for
    return h
Ejemplo n.º 18
0
def getStarredMessages(q: dict) -> str:
    """ get starred messages corresponsing to query (q).
    Include who starred each message
    """
    h = ""
    als = models.Alert.find(q, sort=[('message_id', -1), ('created', -1)])
    starrersByMessage = groupByMessage(als)
    for mess, starrers in starrersByMessage:
        dpr("starrers=%r", starrers)
        starrersH = ", ".join(
            form("<a href='/blog/{u}'>@{u}</a>", u=u) for u in starrers)
        dpr("starrersH=%r", starrersH)
        h += form("<p><br>Starred by {starrers}:</p>\n{m}\n",
                  starrers=starrersH,
                  m=mess.viewH())
        dpr("h=%r", h)
    #//for al
    return h
Ejemplo n.º 19
0
def render(s: str, wikiExt: bool = False) -> Tuple[str, List[str]]:
    """ Render markup into HTML, also return tags
    @param wiki = True if it should be rendered with the WikiLinkExtension
    @return (h,tags) where:
       h:str = rendered html
       tags:List[str] = canonicalised hashtags
    """
    s2 = encloseHashtagAtStart(s)
    s3, tags = GetHashtags(s2).calc()
    dpr("s3=%s", s3)
    if wikiExt:
        markdownWikiProcessor.reset()
        h = markdownWikiProcessor.convert(s3)
    else:
        markdownProcessor.reset()
        h = markdownProcessor.convert(s3)
    dpr("h=%s", h)
    h2 = sanitize(h)
    dpr("h2=%s", h2)
    return (h2, tags)
Ejemplo n.º 20
0
def testForm():
    dpr("- - - in testForm() - - -")
    theTF = TheTestForm()
    theTF.dateOfBirth = BzDate.today()
    dpr("theTF=%r", theTF)
    resultTable = ""

    dpr("request=%r", request)
    if request.method == 'POST':
        theTF = theTF.populateFromRequest(request)
        theTF.copyOfAaa = theTF.aaa
        if theTF.isValid():
            resultTable = getResultTable(theTF)
    #//if

    tem = jinjaEnv.get_template("testForm.html")
    h = tem.render(
        theTF=theTF,
        resultTable=resultTable,
    )
    return h
Ejemplo n.º 21
0
def getPartyLegend(partyStrengths) -> str:
    """ return HTML to go at the top of the chart showing 
    parties, in order of their trend strength, with percentage 
    and color.
    """
    # sort, largest 1st
    ps2 = sorted(partyStrengths, key=lambda ps: ps['strength'])[::-1]
    
    dpr("ps2=%r", ps2)
    h = ""
    for ps in ps2:
        dpr("ps=%r", ps)
        name = ps['name']
        color = ps['color']
        strength = ps['strength']
        h += form("""<span style='color:{color}'>
            {strength:.1f}% {name}</span>&nbsp; """,
            color = color,
            strength = strength,
            name = name)       
    #//for   
    dpr("h=%s", h)
    return h
Ejemplo n.º 22
0
def au_messList():
    lf = MessListFormatter()
    ts = lf.mostRecentTimeStamp()
    tsj = json.dumps({'ts': ts})
    dpr("ts=%r tsj=%r", ts, tsj)
    return tsj
Ejemplo n.º 23
0
def messRep(id=None):
    if id:
        isReply = True
        m = models.Message.getDoc(id)
        mh = m.viewH()
    else:
        isReply = False
        m = None
        mh = ""
    hasPreview = False
    previewH = ""
    tags = None

    mf = MessageForm()
    if request.method == 'POST':
        mf = mf.populateFromRequest(request)

        messRepButton = request.form['messRepButton']
        dpr("messRepButton=%r", messRepButton)
        if mf.isValid():
            if messRepButton == 'preview':
                #>>>>> preview message
                previewH, tags = mark.render(mf.message)
                hasPreview = True
            else:
                #>>>>> create message
                dpr("create new message")
                previewH, tags = mark.render(mf.message)
                newM = models.Message(source=mf.message,
                                      html=previewH,
                                      tags=tags,
                                      author_id=permission.currentUserName())
                if isReply:
                    newM.replyTo_id = id
                newM.save()
                models.notifyTags(tags)
                dpr("newM=%r", newM)
                dpr("tags=%r", tags)
                u = "/mess/" + newM.id()
                dpr("u=%r", u)
                if isReply:
                    al = models.Alert(user_id=m.author_id,
                                      alertType='reply',
                                      message_id=m._id,
                                      doer_id=newM.author_id,
                                      reply_id=newM._id)
                    al.save()
                return redirect(u, code=303)
        #//if valid
    #//if POST

    tem = jinjaEnv.get_template("messRep.html")
    h = tem.render(id=id,
                   isReply=isReply,
                   m=m,
                   mh=mh,
                   mf=mf,
                   msg="",
                   hasPreview=hasPreview,
                   previewH=previewH,
                   tagsH=htmlEsc(repr(tags)))
    return h
Ejemplo n.º 24
0
def au_tag(t):
    lf = TagFormatter(t)
    ts = lf.mostRecentTimeStamp()
    tsj = json.dumps({'ts':ts})
    dpr("ts=%r tsj=%r", ts, tsj)
    return tsj   
Ejemplo n.º 25
0
 def preSave(self):
     self.lastSaved = BzDateTime.now()
     d = self.mongoDict()
     d.pop('anything', "")  # remove the anything field
     dpr("d=%r", d)
     self.anything = d