Created
May 17, 2016 16:56
-
-
Save coreymartella/335f41df484ca26c9d24d719b90e93d8 to your computer and use it in GitHub Desktop.
Ashby Coding Challenge
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* | |
*/ | |
package com.miovision.rss.reader; | |
import java.io.BufferedReader; | |
import java.io.FileNotFoundException; | |
import java.io.InputStreamReader; | |
import java.net.HttpURLConnection; | |
import java.net.URL; | |
import java.text.DateFormat; | |
import java.text.ParseException; | |
import java.text.SimpleDateFormat; | |
import java.util.ArrayList; | |
import java.util.Collections; | |
import java.util.Comparator; | |
import java.util.Date; | |
import java.util.List; | |
import java.util.Locale; | |
/** | |
* @author David Ashby | |
* for Miovision | |
* | |
*/ | |
public class CbcRssParser { | |
private static final String TITLE_START_TAG = "<title>"; | |
private static final String TITLE_END_TAG = "</title>"; | |
private static final String ITEM_START_TAG = "<item"; | |
private static final String ITEM_END_TAG = "</item>"; | |
private static final String CBC_URL = "http://rss.cbc.ca/lineup/topstories.xml"; | |
private static final String LINK_START_TAG = "<link>"; | |
private static final String LINK_END_TAG = "</link>"; | |
private static final String DATE_START_TAG = "<pubDate>"; | |
private static final String DATE_END_TAG = "</pubDate>"; | |
private static final int NUMBER_OF_STORIES = 5; | |
private List<RssStory> getStories() { | |
//-variables defined before they are needed | |
String body = getBody(CBC_URL); | |
return parseBodyToStories(body); | |
} | |
static class StoryComparer implements Comparator<RssStory> { | |
public int compare(RssStory x, RssStory y) | |
{ | |
if (x == y) | |
return 0; | |
else | |
return y.getDate().compareTo(x.getDate()); | |
} | |
} | |
private List<RssStory> parseBodyToStories(String body) { | |
List<RssStory> result = new ArrayList<RssStory>(); | |
int start = 0; | |
while (true) | |
{ | |
//-"<item" should be a constant | |
int nextItemStart = body.indexOf(ITEM_START_TAG, start); | |
int nextItemEnd = body.indexOf(ITEM_END_TAG, nextItemStart); | |
if (nextItemStart < 0 || nextItemEnd < 0) break; | |
String nextItem = body.substring(nextItemStart, nextItemEnd); | |
String title = extractString(nextItem, TITLE_START_TAG, TITLE_END_TAG); | |
String link = extractString(nextItem, LINK_START_TAG, LINK_END_TAG); | |
DateFormat format = new SimpleDateFormat("EEE, dd MMM yyyy HH:MM:SS zzz", Locale.ENGLISH); | |
String dateString = extractString(nextItem, DATE_START_TAG, DATE_END_TAG); | |
Date date = null; | |
try { | |
date = format.parse(dateString); | |
} catch (ParseException e) { | |
System.out.println("Failed to parse date " + dateString); | |
} | |
result.add(new RssStory(title, link, date)); | |
start = nextItemEnd; | |
} | |
return result; | |
} | |
private String extractString(String nextItem, String startTag, String endTag) { | |
return nextItem.substring(nextItem.indexOf(startTag)+startTag.length(), nextItem.indexOf(endTag)); | |
} | |
private String getBody(String url) { | |
String result = ""; | |
try { | |
URL urlUrl = new URL(url); | |
HttpURLConnection conn = (HttpURLConnection) urlUrl.openConnection(); | |
conn.setRequestMethod("GET"); | |
BufferedReader rd = new BufferedReader(new InputStreamReader(conn.getInputStream())); | |
String line; | |
while ((line = rd.readLine()) != null) { | |
result += line; | |
} | |
} | |
catch( FileNotFoundException fnfe) | |
{ | |
System.out.println("Unable to access page" + url); | |
} | |
catch (Exception e) { | |
// | |
throw new RuntimeException(e); | |
} | |
return result; | |
} | |
private void printNStories(List<RssStory> stories, int n) { | |
int index = 0; | |
for (RssStory story : stories) { | |
if (index == n) | |
break; | |
// For debugging | |
// System.out.println(story.getTitle() + " " + story.getDate()); | |
System.out.println(story.getTitle()); | |
index++; | |
} | |
} | |
private void printSortedStories(int numberOfStories) { | |
List<RssStory> listOfStories = getStories(); | |
printNStories(sortList(listOfStories, new StoryComparer()),numberOfStories); | |
} | |
private <T> List<T> sortList(List<T> listOfStories, Comparator<T> comparator) { | |
Collections.sort(listOfStories, comparator); | |
return listOfStories; | |
} | |
public static void main(String[] args) { | |
CbcRssParser parser = new CbcRssParser(); | |
parser.printSortedStories(NUMBER_OF_STORIES); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package com.miovision.rss.reader; | |
import java.util.Date; | |
public class RssStory { | |
private String title; | |
private String link; | |
private Date date; | |
public RssStory(String title, String link, Date date) { | |
this.title = title; | |
this.link = link; | |
this.date = date; | |
} | |
/* (non-Javadoc) | |
* @see java.lang.Object#hashCode() | |
*/ | |
@Override | |
public int hashCode() { | |
// TODO Auto-generated method stub | |
return super.hashCode(); | |
} | |
/* (non-Javadoc) | |
* @see java.lang.Object#equals(java.lang.Object) | |
*/ | |
@Override | |
public boolean equals(Object obj) { | |
// if not an instance of rssStory | |
if(!(obj instanceof RssStory)) | |
{ | |
return false; | |
} | |
RssStory story = (RssStory)obj; | |
// if title is not equal | |
return this.title.equals(story.getTitle()); | |
} | |
public String getTitle() { | |
return title; | |
} | |
public void setTitle(String title) { | |
this.title = title; | |
} | |
public String getLink() { | |
return link; | |
} | |
public void setLink(String link) { | |
this.link = link; | |
} | |
public Date getDate() { | |
return date; | |
} | |
public void setDate(Date date) { | |
this.date = date; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment