Contents:
In a previous assignment, UW Marketing commissioned you to write a route finder tool. Marketing is pleased with your initial results, but now they've asked for a graphical user interface (GUI) that visually draws routes on a map.
You will build your GUI using React (like in the Connect the Dots assignment) and the Spark Framework. Unlike the pathfinder and Connect the Dots assignments, this time you are building both the frontend and the backend! You will get practice using these tools, event-driven programming, and the model-view-controller (MVC) design pattern. You'll probably write less than 50 lines of Java code and about 250 lines of TypeScript to complete the basic requirements.
You are expected to fix any bugs from previous homeworks that affect the correctness or performance of your application in this assignment. You are also required to fix code quality/organization issues in your pathfinder code.
When you're done, you can show off your awesome looking campus-map-route-finding application to your friends and family!
 
    The above diagram is an overview of the basic structure of the application that you'll be building in this assignment. Note that there are two servers this time around. In the Connect the Dots assignment, you had one client (Google Chrome) and one server (the React server). The React server is a part of React, not something you needed to write. It was the React server's job to put all the different parts of your application together before sending it to Google Chrome to be shown to the user. In this application, the React server has the same job.
The additional interesting part of this assignment is the second server, which is a server you'll be writing in Java using the Spark Java framework. There are many more details in the "Backend" section of this assignment spec, but the main job of the Java server is to allow the React application to access the campus paths data. This might take the form of requesting information about buildings on campus, or asking the server to calculate the shortest path between two buildings and respond with the answer. Fortunately, you've already written all the Java code you need to manage this data and perform those calculations, you just need to create a server the allows clients (like your React app running inside Google Chrome) to make requests for data.
In an effort to give you a clear path to completing this assignment, there is a suggested order listed below. You are not required to complete this assignment in this order, but it might be helpful to.
In designing your React frontend in more detail, it may be helpful to read the React documentation's Thinking in React section (as well as maybe the Lifting State Up section for some more gritty details). The "Thinking in React" section walks you through a simple application built in React, and discusses how a React developer might start with an idea of an application and work her way up to having a completely functional application. You certainly don't need to follow that section step-by-step, but it has some suggestions about what to think about when you're designing at a high-level, and your final application needs to use good React style.
        Since you already know the basics of creating a React application from the connect the dots assignment, the
        backend is where you'll encounter the majority of the new material for this assignment. Fortunately, Spark is a
        very simple Java framework that requires very little code to get a fully-featured Java server running. You saw
        Spark in lecture, so we won't be repeating all of the basics here. If you're curious, Spark has some
        documentation on their main webpage, and they also offer  a complete set of javadocs for the API. We're
        providing a class called SparkServer (inside hw-campuspaths-server/) with a
        main method that is where you should create all your routes and do any other initialization that
        you may need to. (For example, you probably want to create an instance of CampusMap that you
        can use to fulfill requests that are sent to your server.) Note that you should not create a new
        CampusMap each time your server receives a request, because then all the work of loading data and
        creating a graph needs to be repeated for each request, slowing your application down.
    
        Creating this application shows us exactly why the Model, View, Controller design pattern is so helpful. You
        originally implemented the CampusMap class to be used with the text user interface from the
        pathfinder assignment, but now you'll be able to reuse parts of it for this assignment without having to modify
        it much (if at all). Separating the model (all your graph code, pathfinding code, and parsing code) from the
        view and controller in the pathfinder application by using CampusMap (and the ModelAPI
        interface that it implements) has made it much easier to reuse all of that code for something completely
        different!
    
        You should implement a Spark Java server that allows other applications to make requests to query data and
        computation from your preexisting pathfinder application. You're writing this server specifically to support the
        React application that you'll be building, so you can design this server to respond to exactly the requests that
        your React application will make. Your SparkServer class shouldn't do much more than contain a the
        main method and define all the different routes in your application - your routes will probably
        only do a very small amount of processing and leave most of the work to calling the methods of a
        CampusMap
        object. You're free to create whatever routes make sense for your overall CampusPaths application, the server
        will probably be very minimal. For reference, the staff solution only has two routes, and those two routes do
        almost no processing other than call methods inside CampusMap. You may modify
        CampusMap,
        but you probably don't need to in order to fulfill the base requirements of this spec, and you should do so
        carefully. In particular, you should not change/break any preexisting functionality - the pathfinder application
        should still work as it did before this assignment.
    
One of the trickiest parts of communicating between two separate programming languages, like Java and TypeScript, is effectively sharing data between them. A Java object works completely different from a TypeScript object, so how are we supposed to send information from the server about paths, and buildings, and other campus data, and have the TypeScript code in your React app be able to understand it? This is where JSON comes in. JSON stands for TypeScript Object Notation: it's a way to take a TypeScript object and turn it into a string that represents it. The powerful thing is that you can also go the other way: take a JSON string and turn it into an actual TypeScript object that you can then pass around, read fields of, and update as you wish. To solve this problem of communication, we're going to have the server always respond to requests by sending a JSON string. That way, the TypeScript code that made the request can just turn the JSON string into an object and read the fields inside that object to get the information it's looking for.
How do we take a Java object inside our server (maybe one that represents a path, or some other data that we want to sent) and turn it into JSON? The folks at Google realized a while back that they had this same problem and invented something called Gson that can do just that. Gson is an extremely powerful and feature-filled Java library, but the basic idea is that it can take a Java object and turn it into a JSON string that contains all the same data. (It can actually go the other direction too, take a JSON string and turn it into a Java object, but that's a much more complicated process and not necessary for this assignment.)
        We now know the basic ideas behind this server: when your React application makes a request to it, one of the
        routes you defined in your Spark server is run. That route's handle method should get any
        additional info from that request (if there is any), and call methods of CampusMap to get the
        information that was requested. Then, the handle method will use Gson to turn the response data
        into a JSON string, and return that JSON string. Spark will take the String you returned from the
        handle method and send it back to your React application that made the request.
    
        To start your server once you've written some code, use the provided hw-campuspaths-server:runSpark
        gradle task. Note that gradle will start the server and then keep running, you won't get a "BUILD SUCCESSFUL"
        message until after you stop the server. Also note that, unlike React, if you change any of your Java code, you
        won't see the changes right away. You'll need to completely stop and re-start your server to have the new
        changes take effect. You'll see in the starter code (SparkServer.main) that there's a CORSFilter
        object that's created, and has the apply method called on it. You should not remove or modify this
        code, and you should leave it at the very top of your main method. This just sets up some extra
        settings to make sure that the React application and the Spark server can talk to each other even though they're
        running on different ports. (React is running on port 3000 and Spark on port 4567 – normally this isn't allowed
        for web security reasons, but the CORSFilter object tells Google Chrome that this is OK.)
    
Once you've got some of your server running, you probably want to test it. Fortunately, you don't need to create the whole GUI before you can test it. Since requests to the sever are just made up of web addresses, you can send a request to your server by hand and see what the results are. (Note that you don't need to do any automated or unit testing for the server code you wrote, manually checking that your server is working is enough.) First, make sure you've started your server and that it's running. Then, open Google Chrome and, in the address bar, type:
localhost:4567/YOUR-ROUTE-HERE
You can replace "YOUR-ROUTE-HERE" with any route that you've defined (and optionally add query parameters as described in the slides from lecture) to send a request to your Spark server. The JSON string that your server sends back will be displayed in the browser window as plain text. Try sending a couple requests for paths between buildings on campus and make sure the server looks like it's sending the right thing back. Congratulations, you're now the proud owner of a shiny new Java web server!
Now that you've created this fancy server, it's time to create a React application that'll use it! Here's your chance to get super creative: you can design your GUI application to look however you want, as long as it meets some basic requirements that we're outlining below. Most of your time on the assignment will probably be spent creating the GUI. While this interface is a little more complicated that what you did in the Connect the Dots assignment, and there isn't as much provided starter code, the core concepts are the same. You're encouraged to look back the the code you wrote in the Connect the Dots assignment and the lecture/section slides and demo code about React to remember how to structure a React app and create your own components.
        You'll be creating your application in hw-campuspaths/, most of your code will go in hw-campuspaths/src/
        and there is a provided image file of the campus map that you should use in hw-campuspaths/public/.
        You are encouraged to use the provided starter code that loads the image and sets up the canvas to be the same
        size as the image. If you want to modify or replace this starter code, you're welcome to, but beware that canvas
        sizing can be very tricky to get right. Note that aesthetics do not matter for this assignment.
        As long as your interface is easily understandable and usable, it doesn't matter how ugly it looks. You're
        welcome and encouraged to make it pretty if you'd like, but wait until you have all the required functionality
        complete first before doing so.
    
        Remember the basic commands for getting your React application up and running: npm install the
        first time you start working on this project, and npm start to get your React server running. You
        should run these commands from hw-campuspaths/. (To see what directory you're currently inside, use
        the pwd command. To change into a directory, use the cd command. This means that if
        you're in the base directory of your repository, use cd hw-campuspaths to change into the correct
        directory.)
    
The following are the requirements for your application to get full credit. Note that a lot of these are open-ended: you're free to choose how to implement them and design the interface for doing so yourself. However, it must be easy and intuitive to understand how to use all the features described below.
Your campus paths GUI must:
hw-campuspaths/public/campus_map.jpg.
        alert()) describing the error and how they might fix it. Your GUI should
            never crash or reach a buggy or invalid state. When in doubt, ask your friend/roommate to try their best
            to cause an error, and make sure your application can handle anything they can throw at it.
        Beyond these requirements as listed, you're allowed to do whatever you'd like to make this application your own. Make sure you've completed the basics of this application before you spend too much time experimenting.
Sometimes your React application will want to send requests to your Spark server to get data to display, this may be in response to some user input, or just as the React application is setting itself up for the first time. TypeScript can make web requests from inside the browser by doing a "fetch".
        A fetch is just like a normal request, as if you were typing a URL into your browser address bar and looking at
        the output in the window. Instead of using the browser GUI, though, you create the URL to request inside
        TypeScript, and the response to the request is returned to you in the TypeScript for you to do whatever you want
        with. The fetch documentation has a
        few sections that'll be particularly important to check out: "Response/Body", and "Checking that the fetch was
        successful". Remember that your application should be able to gracefully handle errors that the server reports
        (or if the server never responds, such as if it was never started). Note that the examples in that documentation
        use the traditional Promise syntax for TypeScript. You're welcome to use that if you'd like, but we highly
        recommend (and support) the async/await syntax for dealing with Promises, which will look different. In
        particular, you won't need calls to .then() or .catch(), instead using keywords like
        await or try/catch blocks. See the section demo code and section slides for more
        information and examples on using fetch to communicate between the server and your React application.
    
In the industry, there are some technologies that can be used for testing GUIs. However, they are often complicated and are definitely beyond the scope of this course, so you don't need to worry about any sort of automated testing for your GUI or your TypeScript.
        Remember to think about where you are in the React lifecycle whenever you're writing code, and make sure that
        what you're doing is always appropriate for that place in the lifecycle. See the Connect the Dots code for
        examples of proper lifecycle management. Make sure you're always using good React style: don't use 
        document.getElementById or similar methods, the only call to ReactDOM should be in index.tsx
        (we provided it for you), and you should use state and props correctly. In the React
        documentation, there is a sidebar on the right labelled "Main Concepts." In that sidebar, sections 5 (State and
        Lifecycle), 10 (Lifting State Up), and 12 (Thinking in React) might come in handy for this assignment in
        particular, and are recommended, though they can be slightly more advanced that we're used to.
    
You're encouraged to express your creativity with this assignment. Once you have a complete, working version of the basic assignment as described above, commit a final working copy to your repository so you'll always be able to go back to it in case you need to. Then, consider implementing some extra features or improving the visual aesthetic of your application.
The only rule for extra features is this: don't break existing rules or feature requirements. None of the things you add should get in the way of your application satisfying the requirements outlined in this spec: you're still bound by those requirements even if you do extra stuff. Outside of that: go crazy! Some ideas are listed below, in no particular order:
ModelAPI and/or CampusMap to allow your server
            to send more data to your React app - you'll need some kind of data that has the building names and their
            x/y locations so they can be drawn on the map.)
        
        For this assignment, you're allowed to edit hw-campuspaths-server/build.gradle and/or hw-campuspaths/package.json
        if you'd like to add additional libraries to help you implement these extra features only. Be absolutely
        sure you know what you're doing, and that you don't change/break any preexisting functionality of those
        files. The staff isn't able to support any additional libraries you may add to your application.
    
        If you decide to add any additional features to your application, document them in 
        hw-campuspaths/extras.txt. If the functionality/features you add show significant effort, you can earn
        some extra credit for this assignment! Note that purely aesthetic changes, like changing the font or the
        background color, aren't enough to warrant extra credit. Only features documented in extras.txt
        will be considered for extra credit. Again, make sure your additional features don't break any of the
        functionality that is required above. Extra credit can help you earn back points that you lost elsewhere in this
        assignment, or might be considered when determining final grades for this course, but it's ultimately a small
        source of additional points.
    
build.gradle
            and package.json that tell gradle and npm to install them for you. You can skip any
            instructions about installation that you might see in their documentation and just import and start using
            them in your code.
        hw-campuspaths-server:runSpark gradle task to compile your new Java and restart the server with
            the changes.
        lsof -i:3000, where you replace the 3000
                    with whatever port number is being used that you need to free up. It'll list all the applications
                    that are using that port, including their PIDs (Process IDs). Find the previous version of the React
                    or Spark server that you created (the React sever might be called "npm" or "node", the Spark server
                    might be called "java"), and find it's PID. You can use the kill PID command to kill
                    that server, just give it the PID of the process you want to kill. Be careful with
                    kill, only kill applications that you personally started and you're sure you want to shut
                    down. It's not a graceful way to stop an application and should be avoided unless absolutely
                    necessary, but it can sometimes be helpful.
                npm start,
            and press Control-C. Remember that you don't need to restart the React server to see changes you make to
            your JS code - changes will be detected automatically by React.
        hw-campuspaths-server:runSpark gradle task. Note that gradle will
            probably complain that the "BUILD FAILED" - you can ignore this message if it was caused by you clicking the
            stop button. Gradle isn't happy about being stopped in the "middle" of what it was doing, but that's fine
            for stopping the server for our purposes.
        export
            default ... line at the bottom of your files! (See the provided JS code for examples.)
        fetch, creating a Spark server, and
            more.
        
        You should pull, then commit and push all changes you made to your model, including and especially your CampusMap
        class. Include all changes/additions you made to the SparkServer class. Additionally, make sure to
        include any changes you may have made to build.gradle and/or package.json, and include
        all of the .tsx and other files that you created in hw-campuspaths/. Don't
        forget to document any extra-credit additions you made in extras.txt.
    
        You should use the tag hw9-final for this assignment.
    
Refer to the assignment submission handout for complete turn in instructions.