-
Notifications
You must be signed in to change notification settings - Fork 55
Home
Due: Thursday 4/14, 12:00pm
The purpose of this assignment is to get familiar with basics of OAuth 2.0 using Passport.js (specifically Twitter), web socket using Socket.io, and integrate software tools to create a social media application. This assignment is divided into two parts: (1) technical lab for Passport.js and Socket.io, and (2) designing a social media application. By the end of this assignment, students comfortable at using Passport.js and Socket.io and design more powerful software with these tools. This is a group-based assignment and you need to work on it within your assigned team (5 people).
- This assignment is intended to be done in a group.
- The assignment may feel overwhelming, so please start early and collaborate with your group!
- The given boilerplate is broken (intentionally). It is your responsibility to fix it.
- We expect that you have completed assignment 0. Any resources you used for assignment 0 are fair game.
- Only Part 2 will be graded. However, since Part 1 provides guidances to Part 2, it is important that you complete Part 1 as well.
- Utilize knowledge from assignment 0 for more complex tools.
- Understand basics of OAuth 2.0 and web socket.
- Utilize Passport.js and Socket.io to create a social media application.
What is an OAuth 2.0? What is a web socket? Why do we need them? Before you jump into the coding portion of this assignment, it is important to understand the high-level concepts of these technical terms. We have provided some resources as an introduction to both OAuth 2.0 and web socket.
For this assignment, we will be using OAuth 2.0 as a way to manage personalized profiles of a user and web socket as live communication between users. Both are essential for most social media application nowadays.
Part 1 of Assignment 1 will be an exercise to help you create a simple social media application with specific tasks. In Part 2 (as mentioned above), you will be creating your own social media application using the skills you acquired in Part 1. Again, Part 1 will not be graded (explicitly), but is a crucial component to do Part 2. The expected result for Part 1 should work similarly to this example app.
Part 1.1 consists of preparation steps before dealing with the main meat of this assignment. It is important that you understand how the following files work before starting Assignment 1: server.js, views/layouts/layout.html, views/index.html, views/chat.html, and public/js/chatbox.js. You may use Piazza, and other online resources to solve your problem(s).
-
Install the following Node.js dependencies: connect-mongo (1.1.0), cookie-parser (1.4.1), dotenv (2.0.0), express-session (1.13.0), method-override (2.3.5), passport (0.3.2), passport-twitter (1.0.4), socket.io (1.4.5)
- You may refer to Assignment 0 to install these dependencies
- Also install dependencies from Assignment 0
- Don't forget to create the directories needed for the database
-
Create your application on Twitter (Twitter Apps Site)
- Website: http://127.0.0.1:3000
- Callback URL: http://127.0.0.1:3000/auth/twitter/callback
-
Store Consumer Key (API Key) and Consumer Secret (API Secret) to
.envfile- Create a file called
.envat the root directory of your project. - Copy and paste the Consumer Key and Consumer Secret given to you by Twitter (from step 2).
- This information is sensitive and SHOULD NOT BE SHARED WITH ANYONE ELSE!
- Your
.envfile should look similar to following:
TWITTER_CONSUMER_KEY=<your consumer key here in quotes> TWITTER_CONSUMER_SECRET=<your consumer secret here in quotes> SESSION_SECRET="4fa238c5d0d632881b6786f3b2d944950169948f"- Make sure
dotenvis loaded inserver.js - Resource: npm dotenv site
- Note that the SESSION_SECRET is static and will be the same for all applications
- Create a file called
-
Uncomment following code:
app.get("/", router.index.view);
Part 1.2 focuses on how to get started with Passport.js, specifically with Passport-Twitter. These tools will help you manage user authentication and Twitter OAuth for Node.js. Keep in mind that Passport.js provides authentication methods beyond Twitter (such as creating secure local login feature or other social media OAuth). To keep things simple for this practice, we will only use the Twitter component of Passport.js. You may use other authentication methods for Part 2. You may use passportjs docs, Piazza, and other online resources to solve your problem(s).
-
Set your Passport middleware in
server.js- The middleware code for Passport is shown below. Copy and paste them to appropriate place.
app.use(passport.initialize()); app.use(passport.session());- What is middleware?
- Most of the middleware codes for this assignment are handled in the given boilerplate.
- Understanding middleware is beyond the purpose of this course, so do not worry if you do not fully understand.
- To learn more about Express's middleware: read this guide on using express middleware
- Try to put Passport middleware code to elsewhere. What happens? (most likely an error or unexpected behavior)
-
Set your Passport serialization in
server.js- The serialization code for Passport is shown below. Copy and paste them to appropriate place.
passport.serializeUser(function(user, done) { done(null, user); }); passport.deserializeUser(function(user, done) { done(null, user); });- To understand what Passport serialization does, read: this stackoverflow question
-
Use Twitter strategy in
server.js- Read and understand: passportjs twitter docs
- The skeleton code for using Twitter strategy is:
passport.use(new strategy.Twitter({ consumerKey: process.env.TWITTER_CONSUMER_KEY, consumerSecret: process.env.TWITTER_CONSUMER_SECRET, callbackURL: "/auth/twitter/callback" }, function(token, token_secret, profile, done) { // What goes here? Refer to step 4. }); -
Write a code to check if user already exists within your application.
- The documentation for Passport-Twitter may use
findOrCreate()function from models (mongoose/MongoDB) to check if user exists or not (if not, then create the user). - For this assignment, we will be using
findOne()function instead. - Resource: stackoverflow
- The skeleton code for this step is:
models.User.findOne({ "twitterID": profile.id }, function(err, user) { // (1) Check if there is an error. If so, return done(err); if(!user) { // (2) since the user is not found, create new user. // Refer to Assignment 0 to how create a new instance of a model return done(null, profile); } else { // (3) since the user is found, update user’s information process.nextTick(function() { return done(null, profile); }); } }); - The documentation for Passport-Twitter may use
-
Create routes for authentication
- Again, refer to passportjs twitter docs to understand how routing for Twitter authentication works.
- You may also want to read passportjs logout docs to create a route for logging a user out.
- Create routes with following spec:
- "/auth/twitter" - GET Request
- "/auth/twitter/callback" - GET Request (success redirect: "/chat" and failure redirect: "/")
- "/logout" - GET Request
-
Create UserSchema in
models.js- The model for User will have (at minimum) following schema:
{ "twitterID": String, "token": String, "username": String, "displayName": String, "photo": String }- Refer to Assignment 0 for creating a schema(s) in
models.js
-
Before you move on, make sure you don't encounter any errors when executing.
- Again, this is bound to happen since given code is intentionally broken.
- If you see any errors, it is your responsibility to fix them.
Part 1.3 will help you experiment with Socket.io. This tool allows you handle live message delivery (live communication between users). One very simple use case of this tool is a chat system. For part 1, we will implement a very basic chat system that is public (private is a bit more complicated, feel free to look into that on your own time ). You may use socket.io docs, Piazza, and other online resources to solve your problem(s).
-
Read and understand: socket.io chat docs.
- We recommend that you also try this tutorial out (preferably on separate project).
- If you do not understand how this tutorial works, please ask before moving on.
-
Uncomment following code in
server.js:io.use(function(socket, next) { session_middleware(socket.request, {}, next); }); -
Create a socket "connection" on
public/js/chatbox.js(client-side)- Your solution for this step should be written in TODO section of
public/js/chatbox.jsfile. - Hint: start with
var socket = io();which will create web socket on client-side. - Grab the text from
#user_inputupon user submitting the form. - Make sure the text in
#user_inputis cleared.
- Your solution for this step should be written in TODO section of
-
Create a socket "connection" on
server.js(server-side)- Hint: start with
io.on("connection", function(socket) { ... });which will handle receiving socket request from client.
- Hint: start with
-
Create a socket called "newsfeed" on both
public/js/chatbox.jsandserver.js- Add the following code to
public/js/chatbox.js:
socket.on("newsfeed", function(data) { var parsedData; // grab and parse data and assign it to the parsedData variable. // other possible solution(s) here. $('#messages').prepend($('<li>').html(messageTemplate(parsedData))); function messageTemplate(parsedData) { // generate HTML text based on some data to be prepended into the list } });- For
server.js, you may create socket for "newsfeed" with following skeleton code:
socket.on("newsfeed", function(msg) { ... // your solution to fill in, see step 7 for details ... io.emit("newsfeed", ...); ... }); - Add the following code to
-
Create NewsFeedSchema in
models.js- The model for NewsFeed will have (at minimum) following schema:
{ "user": String, "message": String, "posted": Date }- Refer to Assignment 0 for creating a schema(s) in
models.js
-
Create a following functionality in
server.js:- Upon receiving request through "newsfeed" socket, create a new instance of NewsFeed model and save it to the database.
- The middleware code given in boilerplate allows you to use
socket.request.session.passport.userto access Passport's user information.- This will grab currently authenticated user in a given "session"
- If there are no authenticated user in that session, then this may throw an error.
- You may use try-catch technique to handle this error: w3schools try catch resource.
- You may also find
JSON.stringify(...)and/orJSON.parse(...)helpful.
-
Before you move on, make sure you don't encounter any errors when executing.
- Again, this is bound to happen since given code is intentionally broken.
- If you see any errors, it is your responsibility to fix them.
- Tip: Check through all the files to see if there are any more "TODO" comments
Now that you have gained technical skills essential for social media, it is your turn to make your own! In Part 2, you will pick a theme/user audience for your social media. Then, create a small-scale social media application that will improve social interaction for that user audience. Unless specified, there are no restrictions for creating your application. Keep in mind, this is a group assignment; everyone should collaborate and contribute to create a well-designed application.
-
Pick a theme and/or a group of user audiences
- Here are examples of a theme (your theme are not limited to these examples):
- a communication tool for academic researchers to share their research paper.
- a communication tool to gather all accountants around the world and share their tips.
- Here are examples of a theme (your theme are not limited to these examples):
-
Create a way for your user audiences to communicate
- Again, you are not required to create a mechanism for private communication (either 1-to-1 or group).
- However, if you feel comfortable and feel that private communication is necessary, you may choose to do so.
-
Required technologies: Node.js, MongoDB, Passport.js, and Socket.io
- You may use other technologies in addition to technologies listed above to facilitate development process
- You may use local login authentication and/or OAuth 2.0 services such as Twitter, Facebook, Instagram, etc.
- It is your responsibility to handle any technical constraints that are not mentioned in Part 1.
- So choose an approach that is most comfortable and beneficial for you.
-
Apply Nielsen's Heuristics
- Refer to course reading materials and lecture slides
- Also: 10 usability heuristics reference
- This means, you should also implement codes for HTML, CSS, and Javascript as well.
- Any violation of a heuristic may result deduction of your grade.
- On your README, please provide a sentence description for each heuristic addressed in your application.
-
Document contribution of each group member
- On your README, please provide brief documentation to show that each group member has contributed fair share of work for Assignment 1, Part 2.
-
Push to GitHub and Deploy to Heroku
- Create your own GitHub repository and Heroku application
- After deploying your application to Heroku, following commands may be needed for OAuth to work successfully. Here's an example for Twitter OAuth:
heroku addons:add mongolab heroku config:set TWITTER_CONSUMER_KEY=<your consumer key without quotes> heroku config:set TWITTER_CONSUMER_SECRET=<your consumer secret without quotes> heroku config:set SESSION_SECRET=4fa238c5d0d632881b6786f3b2d944950169948f
This assignment is out of 20 points and will be graded on Part 2. It will be graded heavily on how you apply design skills taught in COGS 121 using given technologies. Certain points may be awarded for excellent execution of the project (e.g. 2nd criteria will be awarded for application(s) that are truly creative/innovative and improves the communication).
For usability heuristics criteria, following the heuristics is worth 1 point each per heuristic. To receive the full point for a heuristic, you must apply that heuristic somewhere in your application. No use of a heuristic results in 0 points for that heuristic. If you apply a heuristic somewhere in your application, but violate that same heuristic somewhere else in your application, you will only receive 0.5 points for that heuristic. (Note: for some of the heuristics like recognition over recall, applying is the same as not violating, so just worry about not violating that heuristic). For each heuristic, include a one sentence description in the README of how your application addresses that heuristic.
It is expected that each group member contributes to Part 2 fairly. The distribution of work should determined by group consensus and responsibility should be given that member's expertise (either technical or design). Document the distribution of work in the README file.
It is required that your application utilizes Passport.js, this will help us understand if you understood Part 1 of this assignment.
It is not required but highly recommended that your application utilizes Socket.io. As such, it will count as 1 point extra credit.
And YAY! Free points for turning-in Assignment 0 in time.
| Criteria | Points |
|---|---|
| The application follows good usability heuristics with minimal to no violations (and this is documented in the README) | 10 |
| The application has a clear theme and target audience | 2 |
| The application is creative/innovative | 2 |
| The README proves that all group members contributed fairly to this project | 2 |
| INDIVIDUAL: Turned-in Assignment 0 in time | 2 |
| The application effectively utilizes Passport.js to handle user authentication | 2 |
| The application effectively utilizes Socket.io to handle live communication | 1 (extra credit) |
The code/application that you are submitting is what you create in part 2 only, as that is the only portion that is graded. You will need to understand part 1 to be able to complete part 2, but you do not need to submit part 1.
Submission link TBA