Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- >>> ================================ RESTART ================================
- >>>
- testNewsStoryConstructor (__main__.ProblemSet5NewsStory) ... ok
- testNewsStoryGetGuid (__main__.ProblemSet5NewsStory) ... ok
- testNewsStoryGetLink (__main__.ProblemSet5NewsStory) ... ok
- testNewsStoryGetSubject (__main__.ProblemSet5NewsStory) ... ok
- testNewsStoryGetSummary (__main__.ProblemSet5NewsStory) ... ok
- testNewsStoryGetTitle (__main__.ProblemSet5NewsStory) ... ok
- test1TitleTrigger (__main__.ProblemSet5) ... ok
- test2SubjectTrigger (__main__.ProblemSet5) ... ok
- test3SummaryTrigger (__main__.ProblemSet5) ... ok
- test4NotTrigger (__main__.ProblemSet5) ... ok
- test5AndTrigger (__main__.ProblemSet5) ... ok
- test6OrTrigger (__main__.ProblemSet5) ... ok
- test7PhraseTrigger (__main__.ProblemSet5) ... ok
- test8FilterStories (__main__.ProblemSet5) ... ok
- test8FilterStories2 (__main__.ProblemSet5) ... ok
- test9UserTriggers (__main__.ProblemSet5) ... found line!
- # 6.00 Problem Set 5
- # RSS Feed Filter
- import feedparser
- import string
- import time
- from project_util import translate_html
- from news_gui import Popup
- #-----------------------------------------------------------------------
- #
- # Problem Set 5
- #======================
- # Code for retrieving and parsing
- # Google and Yahoo News feeds
- # Do not change this code
- #======================
- def process(url):
- """
- Fetches news items from the rss url and parses them.
- Returns a list of NewsStory-s.
- """
- feed = feedparser.parse(url)
- entries = feed.entries
- ret = []
- for entry in entries:
- guid = entry.guid
- title = translate_html(entry.title)
- link = entry.link
- summary = translate_html(entry.summary)
- try:
- subject = translate_html(entry.tags[0]['term'])
- except AttributeError:
- subject = ""
- newsStory = NewsStory(guid, title, subject, summary, link)
- ret.append(newsStory)
- return ret
- #======================
- # Part 1
- # Data structure design
- #======================
- # Problem 1
- class NewsStory(object):
- def __init__(self, guid, title, subject, summary, link):
- self.guid = guid
- self.title = title
- self.subject = subject
- self.summary = summary
- self.link = link
- def get_guid(self):
- return self.guid
- def get_title(self):
- return self.title
- def get_subject(self):
- return self.subject
- def get_summary(self):
- return self.summary
- def get_link(self):
- return self.link
- #======================
- # Part 2
- # Triggers
- #======================
- class Trigger(object):
- def evaluate(self, story):
- """
- Returns True if an alert should be generated
- for the given news item, or False otherwise.
- """
- raise NotImplementedError
- # Whole Word Triggers
- # Problems 2-5
- class WordTrigger(Trigger):
- def __init__(self, word):
- self.word = word.lower()
- def is_word_in(self, text):
- text = text.lower()
- for e in string.punctuation :
- if e in text: text = text.replace(e, " ")
- return self.word in text.split()
- class TitleTrigger(WordTrigger):
- def evaluate(self, story):
- return self.is_word_in(story.title)
- class SubjectTrigger(WordTrigger):
- def evaluate(self, story):
- return self.is_word_in(story.subject)
- class SummaryTrigger(WordTrigger):
- def evaluate(self, story):
- return self.is_word_in(story.summary)
- # Composite Triggers
- # Problems 6-8
- class NotTrigger(Trigger):
- def __init__(self, trigger):
- self.trigger = trigger
- def evaluate(self, story):
- return not self.trigger.evaluate(story)
- class AndTrigger(Trigger):
- def __init__(self, trigger1, trigger2):
- self.trigger1 = trigger1
- self.trigger2 = trigger2
- def evaluate(self, story):
- return self.trigger1.evaluate(story) and self.trigger2.evaluate(story)
- class OrTrigger(Trigger):
- def __init__(self, trigger1, trigger2):
- self.trigger1 = trigger1
- self.trigger2 = trigger2
- def evaluate(self, story):
- return self.trigger1.evaluate(story) or self.trigger2.evaluate(story)
- # Phrase Trigger
- # Question 9
- class PhraseTrigger(Trigger):
- def __init__(self, phrase):
- self.phrase = phrase
- def evaluate(self, story):
- return (self.phrase in story.title) or (self.phrase in story.subject) or (self.phrase in story.summary)
- #======================
- # Part 3
- # Filtering
- #======================
- def filter_stories(stories, triggerlist):
- """
- Takes in a list of NewsStory-s.
- Returns only those stories for whom
- a trigger in triggerlist fires.
- """
- story_filter = []
- for story in stories:
- for trigger in triggerlist:
- if trigger.evaluate(story) == True:
- story_filter.append(story)
- break
- return story_filter
- #======================
- # Part 4
- # User-Specified Triggers
- #======================
- def readTriggerConfig(filename):
- """
- Returns a list of trigger objects
- that correspond to the rules set
- in the file filename
- """
- triggerfile = open(filename, "r")
- all = [ line.rstrip() for line in triggerfile.readlines() ]
- lines = []
- phrase = ""
- triggers = {}
- trigger_list = []
- for line in all:
- if len(line) == 0 or line[0] == '#':
- continue
- lines.append(line)
- for i in range(len(lines)):
- lines[i] = lines[i].split()
- for e in lines:
- if e[0] == "ADD":
- for x in e[1:]:
- trigger_list.append(triggers[x])
- elif e[1] == "TITLE":
- triggers[e[0]] = TitleTrigger(e[2])
- elif e[1] == "SUBJECT":
- triggers[e[0]] = SubjectTrigger(e[2])
- elif e[1] == "SUMMARY":
- triggers[e[0]] = SummaryTrigger(e[2])
- elif e[1] == "NOT":
- triggers[e[0]] = NotTrigger(triggers[e[2]])
- elif e[1] == "AND":
- triggers[e[0]] = AndTrigger(triggers[e[2]], triggers[e[3]])
- elif e[1] == "OR":
- triggers[e[0]] = OrTrigger(triggers[e[2]], triggers[e[3]])
- elif e[1] == "PHRASE":
- phrase = e[2]
- for x in e[3:]:
- phrase += " " + x
- triggers[e[0]] = PhraseTrigger(phrase)
- return trigger_list
- import thread
- def main_thread(p):
- # A sample trigger list - you'll replace
- # this with something more configurable in Problem 11
- # t1 = SubjectTrigger("Obama")
- # t2 = SummaryTrigger("MIT")
- # t3 = PhraseTrigger("Supreme Court")
- # t4 = OrTrigger(t2, t3)
- # triggerlist = [t1, t4]
- # TODO: Problem 11
- # After implementing readTriggerConfig, uncomment this line
- triggerlist = readTriggerConfig("triggers.txt")
- print triggerlist
- guidShown = []
- while True:
- print "Polling..."
- # Get stories from Google's Top Stories RSS news feed
- stories = process("http://news.google.com/?output=rss")
- # Get stories from Yahoo's Top Stories RSS news feed
- stories.extend(process("http://rss.news.yahoo.com/rss/topstories"))
- # Only select stories we're interested in
- stories = filter_stories(stories, triggerlist)
- # Don't print a story if we have already printed it before
- newstories = []
- for story in stories:
- if story.get_guid() not in guidShown:
- newstories.append(story)
- for story in newstories:
- guidShown.append(story.get_guid())
- p.newWindow(story)
- print "Sleeping..."
- time.sleep(SLEEPTIME)
- SLEEPTIME = 60 #seconds -- how often we poll
- class Trigger(object):
- def evaluate():
- return False
- class WordTrigger(Trigger):
- def __init__(self, word):
- self.word = word.lower()
- print "Injected!"
- def hash(self):
- raise NotImplementedError
- class SubjectTrigger(Trigger):
- def __init__(self, word):
- self.word = word.lower()
- print "Injected Subject!"
- def hash(self):
- return "SUBJECT-" + self.word
- class TitleTrigger(WordTrigger):
- def hash(self):
- return "TITLE-" + self.word
- class SummaryTrigger(WordTrigger):
- def hash(self):
- return "SUMMARY-" + self.word
- class NotTrigger(Trigger):
- def __init__(self, trigger):
- self.trigger = trigger
- print "Injected!"
- def hash(self):
- return "NOT-" + self.trigger.hash()
- class PhraseTrigger(Trigger):
- def __init__(self, phrase):
- self.phrase = phrase
- print "Injected!"
- def hash(self):
- return "PHRASE-" + self.phrase
- class CompositeTrigger(Trigger):
- def __init__(self, trigger1, trigger2):
- self.trigger1 = trigger1
- self.trigger2 = trigger2
- class AndTrigger(CompositeTrigger):
- def hash(self):
- t1_hash = self.trigger1.hash()
- t2_hash = self.trigger2.hash()
- if t1_hash > t2_hash:
- return "AND-" + t1_hash + "-" + t2_hash
- else:
- return "AND-" + t2_hash + "-" + t1_hash
- class OrTrigger(CompositeTrigger):
- def hash(self):
- t1_hash = self.trigger1.hash()
- t2_hash = self.trigger2.hash()
- if t1_hash > t2_hash:
- return "OR-" + t1_hash + "-" + t2_hash
- else:
- return "OR-" + t2_hash + "-" + t1_hash
- Injected Subject!
- Injected!
- Injected!
- {'SUBJECT-sports': False, 'OR-SUMMARY-obama-PHRASE-Hillary Clinton': False}
- ERROR
- ======================================================================
- ERROR: test9UserTriggers (__main__.ProblemSet5)
- ----------------------------------------------------------------------
- Traceback (most recent call last):
- File "/home/sakh/MIT/6.00 Intro to CS/ps5/ps5_test.py", line 269, in test9UserTriggers
- trigger_list = readTriggerConfig("triggers.txt")
- File "compile-errors", line 205, in readTriggerConfig
- NameError: global name 'TitleTrigger' is not defined
- ----------------------------------------------------------------------
- Ran 16 tests in 0.495s
- FAILED (errors=1)
Advertisement
Add Comment
Please, Sign In to add comment