For the following questions, you will implement the data structure to.pdfarjunhassan8
For the following questions, you will implement the data structure to store information used by a
local car dealer. Each car has some information and stored in a text files called cars: Write a
main program for all questions to let the user enter, delete, search for information, and print
current cars stored in the data structure. Cars formatted so car records separated by a blank line.
Each record contains (in order, each in a single line): Make (manufacturer). Model, Year,
Mileage, Price. Implement a double linked-list to store cars data. Write a double linked-list class
including search, delete, append (to the head and tail), and remove (from the head and tail).
Implement a FIFO queue of car data using the double linked-list. You can use the double linked
list you wrote in Q1. Implement a max-heap of cars data that can extract the car with the highest
price. Write a max-heap class including heapify, build heap, extract, and insertion. Implement a
binary search tree of car data. Write a BST class including search, insertion, and deletion.
Solution
Cars.java
package pacages;
public class Cars {
String make;
String model;
int year;
double mileage;
double price;
// Setters and getters for the Cars member variables
public String getMake() {
return make;
}
public void setMake(String make) {
this.make = make;
}
public String getModel() {
return model;
}
public void setModel(String model) {
this.model = model;
}
public int getYear() {
return year;
}
public void setYear(int year) {
this.year = year;
}
public double getMileage() {
return mileage;
}
public void setMileage(double mileage) {
this.mileage = mileage;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
public String toString()
{
return \"Make: \"+getMake()+ \" Model: \"+getModel()+ \" Year: \"+getYear() + \"
Mileage: \"+getMileage() + \" Price: \"+getPrice();
}
}
DoublyLinkedList.java
package pacages;
class Node
{
protected Cars data;
protected Node next, prev;
/* Constructor */
public Node()
{
next = null;
prev = null;
data = null;
}
/* Constructor */
public Node(Cars d, Node n, Node p)
{
data = d;
next = n;
prev = p;
}
/* Function to set link to next node */
public void setLinkNext(Node n)
{
next = n;
}
/* Function to set link to previous node */
public void setLinkPrev(Node p)
{
prev = p;
}
/* Funtion to get link to next node */
public Node getLinkNext()
{
return next;
}
/* Function to get link to previous node */
public Node getLinkPrev()
{
return prev;
}
/* Function to set data to node */
public void setData(Cars d)
{
data = d;
}
/* Function to get data from node */
public Cars getData()
{
return data;
}
}
/* Class linkedList */
public class DoublyLinkedList
{
protected Node start;
protected Node end ;
public int size;
/* Constructor */
public DoublyLinkedList()
{
start = null;
end = null;
size = 0;
}
/* Function to check if list is empty */
public boolean isEmpty()
{
return start == null;
}
/* Function to get size of list */
public.
A presentation made for the NG-CONF Israel that took place in jun 2014 at Google TLV Campus (http://ng-conf.gdg.co.il/)
its an overview of how to use ngRoute and UI-Router in your app this slideshow contain a link for a working demo
Maciej Treder ''Angular Universal - a medicine for the Angular + SEO/CDN issu...OdessaJS Conf
Are you ready for production? Are you sure? Is your application prefetchable? Is it readable for search engine robots? Will it fit into Content Delivery Network? Do you want to make it even faster? Meet the Server-Side Rendering concept. Learn how to bring first meaningful paint immediately, work with server-side Angular code, optimize API calls and more!
Domain Driven Design (DDD) is a topic that's been gaining a lot of popularity in both the Java and .NET camps recently. Entities, value types, repositories, bounded contexts and anti-corruption layers -- find out what all the buzz is about, and how establishing a domain model can help you combat complexity in your code.
Richard Dingwall is a .NET developer and blogger with a passion for architecture and maintainable code.
He is currently working at Provoke Solutions as lead developer on a six-month project introducing test-driven development (TDD) and domain-driven design (DDD) to a large ASP.NET ERP system.
An hour-long talk given at Wellington .NET user group, Sept 23 2009.
Through this presentation you will gain a good understanding of how the clean architecture pattern is implemented at Taxibeat. What issues the Android Taxibeat team has faced so far and what solutions we came up with. Of course, the benefits of clean architecture will also be discussed along with the way we managed to build two fast paced iterative apps that share functionality.
For the following questions, you will implement the data structure to.pdfarjunhassan8
For the following questions, you will implement the data structure to store information used by a
local car dealer. Each car has some information and stored in a text files called cars: Write a
main program for all questions to let the user enter, delete, search for information, and print
current cars stored in the data structure. Cars formatted so car records separated by a blank line.
Each record contains (in order, each in a single line): Make (manufacturer). Model, Year,
Mileage, Price. Implement a double linked-list to store cars data. Write a double linked-list class
including search, delete, append (to the head and tail), and remove (from the head and tail).
Implement a FIFO queue of car data using the double linked-list. You can use the double linked
list you wrote in Q1. Implement a max-heap of cars data that can extract the car with the highest
price. Write a max-heap class including heapify, build heap, extract, and insertion. Implement a
binary search tree of car data. Write a BST class including search, insertion, and deletion.
Solution
Cars.java
package pacages;
public class Cars {
String make;
String model;
int year;
double mileage;
double price;
// Setters and getters for the Cars member variables
public String getMake() {
return make;
}
public void setMake(String make) {
this.make = make;
}
public String getModel() {
return model;
}
public void setModel(String model) {
this.model = model;
}
public int getYear() {
return year;
}
public void setYear(int year) {
this.year = year;
}
public double getMileage() {
return mileage;
}
public void setMileage(double mileage) {
this.mileage = mileage;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
public String toString()
{
return \"Make: \"+getMake()+ \" Model: \"+getModel()+ \" Year: \"+getYear() + \"
Mileage: \"+getMileage() + \" Price: \"+getPrice();
}
}
DoublyLinkedList.java
package pacages;
class Node
{
protected Cars data;
protected Node next, prev;
/* Constructor */
public Node()
{
next = null;
prev = null;
data = null;
}
/* Constructor */
public Node(Cars d, Node n, Node p)
{
data = d;
next = n;
prev = p;
}
/* Function to set link to next node */
public void setLinkNext(Node n)
{
next = n;
}
/* Function to set link to previous node */
public void setLinkPrev(Node p)
{
prev = p;
}
/* Funtion to get link to next node */
public Node getLinkNext()
{
return next;
}
/* Function to get link to previous node */
public Node getLinkPrev()
{
return prev;
}
/* Function to set data to node */
public void setData(Cars d)
{
data = d;
}
/* Function to get data from node */
public Cars getData()
{
return data;
}
}
/* Class linkedList */
public class DoublyLinkedList
{
protected Node start;
protected Node end ;
public int size;
/* Constructor */
public DoublyLinkedList()
{
start = null;
end = null;
size = 0;
}
/* Function to check if list is empty */
public boolean isEmpty()
{
return start == null;
}
/* Function to get size of list */
public.
A presentation made for the NG-CONF Israel that took place in jun 2014 at Google TLV Campus (http://ng-conf.gdg.co.il/)
its an overview of how to use ngRoute and UI-Router in your app this slideshow contain a link for a working demo
Maciej Treder ''Angular Universal - a medicine for the Angular + SEO/CDN issu...OdessaJS Conf
Are you ready for production? Are you sure? Is your application prefetchable? Is it readable for search engine robots? Will it fit into Content Delivery Network? Do you want to make it even faster? Meet the Server-Side Rendering concept. Learn how to bring first meaningful paint immediately, work with server-side Angular code, optimize API calls and more!
Domain Driven Design (DDD) is a topic that's been gaining a lot of popularity in both the Java and .NET camps recently. Entities, value types, repositories, bounded contexts and anti-corruption layers -- find out what all the buzz is about, and how establishing a domain model can help you combat complexity in your code.
Richard Dingwall is a .NET developer and blogger with a passion for architecture and maintainable code.
He is currently working at Provoke Solutions as lead developer on a six-month project introducing test-driven development (TDD) and domain-driven design (DDD) to a large ASP.NET ERP system.
An hour-long talk given at Wellington .NET user group, Sept 23 2009.
Through this presentation you will gain a good understanding of how the clean architecture pattern is implemented at Taxibeat. What issues the Android Taxibeat team has faced so far and what solutions we came up with. Of course, the benefits of clean architecture will also be discussed along with the way we managed to build two fast paced iterative apps that share functionality.
PHP Frameworks: I want to break free (IPC Berlin 2024)Ralf Eggert
In this presentation, we examine the challenges and limitations of relying too heavily on PHP frameworks in web development. We discuss the history of PHP and its frameworks to understand how this dependence has evolved. The focus will be on providing concrete tips and strategies to reduce reliance on these frameworks, based on real-world examples and practical considerations. The goal is to equip developers with the skills and knowledge to create more flexible and future-proof web applications. We'll explore the importance of maintaining autonomy in a rapidly changing tech landscape and how to make informed decisions in PHP development.
This talk is aimed at encouraging a more independent approach to using PHP frameworks, moving towards a more flexible and future-proof approach to PHP development.
DevOps and Testing slides at DASA ConnectKari Kakkonen
My and Rik Marselis slides at 30.5.2024 DASA Connect conference. We discuss about what is testing, then what is agile testing and finally what is Testing in DevOps. Finally we had lovely workshop with the participants trying to find out different ways to think about quality and testing in different parts of the DevOps infinity loop.
Search and Society: Reimagining Information Access for Radical FuturesBhaskar Mitra
The field of Information retrieval (IR) is currently undergoing a transformative shift, at least partly due to the emerging applications of generative AI to information access. In this talk, we will deliberate on the sociotechnical implications of generative AI for information access. We will argue that there is both a critical necessity and an exciting opportunity for the IR community to re-center our research agendas on societal needs while dismantling the artificial separation between the work on fairness, accountability, transparency, and ethics in IR and the rest of IR research. Instead of adopting a reactionary strategy of trying to mitigate potential social harms from emerging technologies, the community should aim to proactively set the research agenda for the kinds of systems we should build inspired by diverse explicitly stated sociotechnical imaginaries. The sociotechnical imaginaries that underpin the design and development of information access technologies needs to be explicitly articulated, and we need to develop theories of change in context of these diverse perspectives. Our guiding future imaginaries must be informed by other academic fields, such as democratic theory and critical theory, and should be co-developed with social science scholars, legal scholars, civil rights and social justice activists, and artists, among others.
Neuro-symbolic is not enough, we need neuro-*semantic*Frank van Harmelen
Neuro-symbolic (NeSy) AI is on the rise. However, simply machine learning on just any symbolic structure is not sufficient to really harvest the gains of NeSy. These will only be gained when the symbolic structures have an actual semantics. I give an operational definition of semantics as “predictable inference”.
All of this illustrated with link prediction over knowledge graphs, but the argument is general.
UiPath Test Automation using UiPath Test Suite series, part 4DianaGray10
Welcome to UiPath Test Automation using UiPath Test Suite series part 4. In this session, we will cover Test Manager overview along with SAP heatmap.
The UiPath Test Manager overview with SAP heatmap webinar offers a concise yet comprehensive exploration of the role of a Test Manager within SAP environments, coupled with the utilization of heatmaps for effective testing strategies.
Participants will gain insights into the responsibilities, challenges, and best practices associated with test management in SAP projects. Additionally, the webinar delves into the significance of heatmaps as a visual aid for identifying testing priorities, areas of risk, and resource allocation within SAP landscapes. Through this session, attendees can expect to enhance their understanding of test management principles while learning practical approaches to optimize testing processes in SAP environments using heatmap visualization techniques
What will you get from this session?
1. Insights into SAP testing best practices
2. Heatmap utilization for testing
3. Optimization of testing processes
4. Demo
Topics covered:
Execution from the test manager
Orchestrator execution result
Defect reporting
SAP heatmap example with demo
Speaker:
Deepak Rai, Automation Practice Lead, Boundaryless Group and UiPath MVP
GDG Cloud Southlake #33: Boule & Rebala: Effective AppSec in SDLC using Deplo...James Anderson
Effective Application Security in Software Delivery lifecycle using Deployment Firewall and DBOM
The modern software delivery process (or the CI/CD process) includes many tools, distributed teams, open-source code, and cloud platforms. Constant focus on speed to release software to market, along with the traditional slow and manual security checks has caused gaps in continuous security as an important piece in the software supply chain. Today organizations feel more susceptible to external and internal cyber threats due to the vast attack surface in their applications supply chain and the lack of end-to-end governance and risk management.
The software team must secure its software delivery process to avoid vulnerability and security breaches. This needs to be achieved with existing tool chains and without extensive rework of the delivery processes. This talk will present strategies and techniques for providing visibility into the true risk of the existing vulnerabilities, preventing the introduction of security issues in the software, resolving vulnerabilities in production environments quickly, and capturing the deployment bill of materials (DBOM).
Speakers:
Bob Boule
Robert Boule is a technology enthusiast with PASSION for technology and making things work along with a knack for helping others understand how things work. He comes with around 20 years of solution engineering experience in application security, software continuous delivery, and SaaS platforms. He is known for his dynamic presentations in CI/CD and application security integrated in software delivery lifecycle.
Gopinath Rebala
Gopinath Rebala is the CTO of OpsMx, where he has overall responsibility for the machine learning and data processing architectures for Secure Software Delivery. Gopi also has a strong connection with our customers, leading design and architecture for strategic implementations. Gopi is a frequent speaker and well-known leader in continuous delivery and integrating security into software delivery.
GraphRAG is All You need? LLM & Knowledge GraphGuy Korland
Guy Korland, CEO and Co-founder of FalkorDB, will review two articles on the integration of language models with knowledge graphs.
1. Unifying Large Language Models and Knowledge Graphs: A Roadmap.
https://arxiv.org/abs/2306.08302
2. Microsoft Research's GraphRAG paper and a review paper on various uses of knowledge graphs:
https://www.microsoft.com/en-us/research/blog/graphrag-unlocking-llm-discovery-on-narrative-private-data/
"Impact of front-end architecture on development cost", Viktor TurskyiFwdays
I have heard many times that architecture is not important for the front-end. Also, many times I have seen how developers implement features on the front-end just following the standard rules for a framework and think that this is enough to successfully launch the project, and then the project fails. How to prevent this and what approach to choose? I have launched dozens of complex projects and during the talk we will analyze which approaches have worked for me and which have not.
Empowering NextGen Mobility via Large Action Model Infrastructure (LAMI): pav...
Creating an Uber Clone - Part XXVI - Transcript.pdf
1. Creating an Uber Clone - Part XXVI
Before we proceed into the actual driver app work & push notification we need to implement all the infrastructure in the server side. I also need to implement some
changes we need in the protocol.
2. private String hailingFrom;
private String hailingTo;
private String pushToken;
public RideDAO getRideDao() {
return new RideDAO(id, givenName, hailingFrom, hailingTo);
}
public UserDAO getDao() {
return new UserDAO(id, givenName, surname, phone, email,
facebookId, googleId, driver, car, currentRating,
latitude, longitude, direction, pushToken);
}
public UserDAO getPartialDao() {
return new UserDAO(id, givenName, surname, null, null,
null, null, driver, car, currentRating, latitude,
longitude, direction, pushToken);
}
User (Server)
Lets start by looking at the User class. I had to add 3 new fields and modify/add some methods.
hailingFrom & hailingTo allow us to communicate our trip details with the driver community
3. private String hailingFrom;
private String hailingTo;
private String pushToken;
public RideDAO getRideDao() {
return new RideDAO(id, givenName, hailingFrom, hailingTo);
}
public UserDAO getDao() {
return new UserDAO(id, givenName, surname, phone, email,
facebookId, googleId, driver, car, currentRating,
latitude, longitude, direction, pushToken);
}
public UserDAO getPartialDao() {
return new UserDAO(id, givenName, surname, null, null,
null, null, driver, car, currentRating, latitude,
longitude, direction, pushToken);
}
User (Server)
I need the pushToken of drivers so we can hail them directly from the app
4. private String hailingFrom;
private String hailingTo;
private String pushToken;
public RideDAO getRideDao() {
return new RideDAO(id, givenName, hailingFrom, hailingTo);
}
public UserDAO getDao() {
return new UserDAO(id, givenName, surname, phone, email,
facebookId, googleId, driver, car, currentRating,
latitude, longitude, direction, pushToken);
}
public UserDAO getPartialDao() {
return new UserDAO(id, givenName, surname, null, null,
null, null, driver, car, currentRating, latitude,
longitude, direction, pushToken);
}
User (Server)
I'll discuss the `RideDAO` class soon, it allows us to send details about the trip to drivers
5. private String hailingFrom;
private String hailingTo;
private String pushToken;
public RideDAO getRideDao() {
return new RideDAO(id, givenName, hailingFrom, hailingTo);
}
public UserDAO getDao() {
return new UserDAO(id, givenName, surname, phone, email,
facebookId, googleId, driver, car, currentRating,
latitude, longitude, direction, pushToken);
}
public UserDAO getPartialDao() {
return new UserDAO(id, givenName, surname, null, null,
null, null, driver, car, currentRating, latitude,
longitude, direction, pushToken);
}
User (Server)
Not much of a change but I added the pushToken to the UserDAO factory methods
6. public class RideDAO implements Serializable {
private long userId;
private String name;
private String from;
private String destination;
public RideDAO() {
}
public RideDAO(long userId, String name, String from, String destination) {
this.userId = userId;
this.name = name;
if(this.name == null) {
this.name = "[Unnamed User]";
}
this.from = from;
this.destination = destination;
}
// getters and setters trimmed out
}
RideDAO
The RideDAO class is a pretty trivial object. There's no point in enumerating the details of this class as it's pretty simple. The main usage for this is in the new RideService
which I will get to soon but first we need to discuss the Ride class.
7. @Entity
public class Ride {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
@ManyToOne
private User passenger;
@ManyToOne
private User driver;
@OneToMany
@OrderBy("time ASC")
private Set<Waypoint> route;
private BigDecimal cost;
private String currency;
private boolean finished;
private boolean started;
// trimmed out constructors, getters and setters
}
Ride
Ride isn't as simple as RideDAO despite their common name. It contains far more information. Currently we don't use all of that but the fact that it's logged will let you
provide all of that information within the app or a management app easily.
The Ride class is a JPA entity similar to the User class.
I used an auto-increment value for the id instead of a random string. I wanted to keep things simple but notice this can expose a security vulnerability of scanning for
rides…
8. @Entity
public class Ride {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
@ManyToOne
private User passenger;
@ManyToOne
private User driver;
@OneToMany
@OrderBy("time ASC")
private Set<Waypoint> route;
private BigDecimal cost;
private String currency;
private boolean finished;
private boolean started;
// trimmed out constructors, getters and setters
}
Ride
The passenger & driver are relational database references to the respective database objects representing each one of them
9. @Entity
public class Ride {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
@ManyToOne
private User passenger;
@ManyToOne
private User driver;
@OneToMany
@OrderBy("time ASC")
private Set<Waypoint> route;
private BigDecimal cost;
private String currency;
private boolean finished;
private boolean started;
// trimmed out constructors, getters and setters
}
Ride
The route itself is a set of waypoints sorted by the time associated with the given waypoint. We'll discuss waypoints soon enough but technically it's just a set of
coordinates
10. @Entity
public class Ride {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
@ManyToOne
private User passenger;
@ManyToOne
private User driver;
@OneToMany
@OrderBy("time ASC")
private Set<Waypoint> route;
private BigDecimal cost;
private String currency;
private boolean finished;
private boolean started;
// trimmed out constructors, getters and setters
}
Ride
I really oversimplified the cost field. It should work for sum and currency but it's usually not as simple as that. It's important to use something like BigDecimal and not
double when dealing with financial numbers as double is built for scientific usage and has rounding errors
11. @Entity
public class Ride {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
@ManyToOne
private User passenger;
@ManyToOne
private User driver;
@OneToMany
@OrderBy("time ASC")
private Set<Waypoint> route;
private BigDecimal cost;
private String currency;
private boolean finished;
private boolean started;
// trimmed out constructors, getters and setters
}
Ride
We have two boolean flags, a ride is started once a passenger is picked up. It’s finished once he is dropped off or if the ride was canceled
12. public interface RideRepository extends CrudRepository<Ride, Long> {
@Query("select b from Ride b where b.finished = false and b.driver.id = ?1")
public List<Ride> findByNotFinishedUser(long id);
}
RideRepository
The companion CRUD RideRepository is pretty standard with one big exception. I added a special case finder that lets us locate the User that is currently hailing a car.
Notice the syntax b.driver.id = ?1 which points through the relation to the driver object.
13. @Entity
public class Waypoint {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private Long id;
private long time;
private double latitude;
private double longitude;
private float direction;
// trimmed out constructors, getters and setters
}
Waypoint
The Waypoint entity referenced from the Ride entity is pretty trivial. Notice we still need a unique id for a waypoint even if we don't actually use it in code...
The interesting part here is the time value which is the value of System.currentTimeMillis(). This allows us to build a path based on the time sequence. It will also allow us
to reconstruct a trip and generate additional details such as speed/cost if we wish to do that in the future.
Notice that there is also a WaypointRepository interface. I’m skipping it as it contains no actual code
14. @Service
public class RideService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Transactional
public UserDAO hailCar(String token, boolean h, String from, String to) {
User u = users.findByAuthToken(token).get(0);
if(h) {
if(u.getAssignedUser() != null) {
long driverId = u.getAssignedUser();
u.setAssignedUser(null);
users.save(u);
User driver = users.findOne(driverId);
return driver.getPartialDao();
}
} else {
u.setAssignedUser(null);
}
u.setHailing(h);
u.setHailingFrom(from);
u.setHailingTo(to);
users.save(u);
return null;
}
RideService
The RideService class serves the same purpose as the UserService class focusing on rides and driver related features. I could have just stuck all of this logic into one
huge class but separating functionality to different service classes based on logic makes sense.
We manipulate both the rides and users CRUD objects from this class
15. @Service
public class RideService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Transactional
public UserDAO hailCar(String token, boolean h, String from, String to) {
User u = users.findByAuthToken(token).get(0);
if(h) {
if(u.getAssignedUser() != null) {
long driverId = u.getAssignedUser();
u.setAssignedUser(null);
users.save(u);
User driver = users.findOne(driverId);
return driver.getPartialDao();
}
} else {
u.setAssignedUser(null);
}
u.setHailing(h);
u.setHailingFrom(from);
u.setHailingTo(to);
users.save(u);
return null;
}
RideService
Hailing is a transactional method, this means that all operations within the method will either succeed or fail depending on the outcome. This is important to prevent an
inconsistent state in the database
16. @Service
public class RideService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Transactional
public UserDAO hailCar(String token, boolean h, String from, String to) {
User u = users.findByAuthToken(token).get(0);
if(h) {
if(u.getAssignedUser() != null) {
long driverId = u.getAssignedUser();
u.setAssignedUser(null);
users.save(u);
User driver = users.findOne(driverId);
return driver.getPartialDao();
}
} else {
u.setAssignedUser(null);
}
u.setHailing(h);
u.setHailingFrom(from);
u.setHailingTo(to);
users.save(u);
return null;
}
RideService
This method can be invoked to start and stop hailing. In this case we use the assigned user property to detect if a driver accepted the ride. If so we return the driver data
to the client
17. users.save(u);
return null;
}
public RideDAO getRideData(long userId) {
User u = users.findOne(userId);
if(u == null) {
return null;
}
return u.getRideDao();
}
@Transactional
public long acceptRide(String token, long userId) {
User driver = users.findByAuthToken(token).get(0);
User passenger = users.findOne(userId);
if(!passenger.isHailing()) {
throw new RuntimeException("Not hailing");
}
passenger.setHailing(false);
passenger.setAssignedUser(driver.getId());
driver.setAssignedUser(userId);
users.save(driver);
users.save(passenger);
Ride r = new Ride();
r.setDriver(driver);
r.setPassenger(passenger);
rides.save(r);
RideService
When a driver gets a notification of a ride he invokes this method to get back the data about the ride
18. users.save(u);
return null;
}
public RideDAO getRideData(long userId) {
User u = users.findOne(userId);
if(u == null) {
return null;
}
return u.getRideDao();
}
@Transactional
public long acceptRide(String token, long userId) {
User driver = users.findByAuthToken(token).get(0);
User passenger = users.findOne(userId);
if(!passenger.isHailing()) {
throw new RuntimeException("Not hailing");
}
passenger.setHailing(false);
passenger.setAssignedUser(driver.getId());
driver.setAssignedUser(userId);
users.save(driver);
users.save(passenger);
Ride r = new Ride();
r.setDriver(driver);
r.setPassenger(passenger);
rides.save(r);
RideService
If the driver wishes to accept the ride he invokes this transactional method. The method accepts the token from the driver and the id of the user hailing the ride. It creates
a new Ride entity and returns its ID, from this point on we need to refer to the Ride id and not the user id or token
19. User driver = users.findByAuthToken(token).get(0);
User passenger = users.findOne(userId);
if(!passenger.isHailing()) {
throw new RuntimeException("Not hailing");
}
passenger.setHailing(false);
passenger.setAssignedUser(driver.getId());
driver.setAssignedUser(userId);
users.save(driver);
users.save(passenger);
Ride r = new Ride();
r.setDriver(driver);
r.setPassenger(passenger);
rides.save(r);
return r.getId();
}
public void startRide(long rideId) {
Ride current = rides.findOne(rideId);
current.setStarted(true);
rides.save(current);
}
public void finishRide(long rideId) {
Ride current = rides.findOne(rideId);
current.setFinished(true);
rides.save(current);
}
}
RideService
Start ride and finish ride are invoked by the driver when he picks up the passenger and when he drops him off. Normally, finish ride should also handle elements like
billing etc. but I won't go into that now
20. @Controller
@RequestMapping("/ride")
public class RideWebservice {
@Autowired
private RideService rides;
@RequestMapping(method=RequestMethod.GET,value = "/get")
public @ResponseBody RideDAO getRideData(long id) {
return rides.getRideData(id);
}
@RequestMapping(method=RequestMethod.GET,value="/accept")
public @ResponseBody String acceptRide(@RequestParam(name="token", required = true) String token,
@RequestParam(name="userId", required = true) long userId) {
long val = rides.acceptRide(token, userId);
return "" + val;
}
@RequestMapping(method=RequestMethod.POST,value="/start")
public @ResponseBody String startRide(@RequestParam(name="id", required = true) long rideId) {
rides.startRide(rideId);
return "OK";
}
@RequestMapping(method=RequestMethod.POST,value="/finish")
public @ResponseBody String finishRide(@RequestParam(name="id", required = true) long rideId) {
rides.finishRide(rideId);
return "OK";
}
}
RideWebservice
The next step is bridging this to the user through a webservice...
The RideWebservice class exposes the RideService calls almost verbatim to the client.
The get call fetches the RideDAO for the given user id
21. @Controller
@RequestMapping("/ride")
public class RideWebservice {
@Autowired
private RideService rides;
@RequestMapping(method=RequestMethod.GET,value = "/get")
public @ResponseBody RideDAO getRideData(long id) {
return rides.getRideData(id);
}
@RequestMapping(method=RequestMethod.GET,value="/accept")
public @ResponseBody String acceptRide(@RequestParam(name="token", required = true) String token,
@RequestParam(name="userId", required = true) long userId) {
long val = rides.acceptRide(token, userId);
return "" + val;
}
@RequestMapping(method=RequestMethod.POST,value="/start")
public @ResponseBody String startRide(@RequestParam(name="id", required = true) long rideId) {
rides.startRide(rideId);
return "OK";
}
@RequestMapping(method=RequestMethod.POST,value="/finish")
public @ResponseBody String finishRide(@RequestParam(name="id", required = true) long rideId) {
rides.finishRide(rideId);
return "OK";
}
}
RideWebservice
Start and finish rides are again very simple with only one argument which is the ride id
22. public void updatePushToken(String token, String pushToken) {
User u = users.findByAuthToken(token).get(0);
u.setPushToken(pushToken);
users.save(u);
}
UserService
We also have to add some minor changes to the UserService and LocationService classes. Lets start with the UserService class. Drivers need a push token so we can
hail them. This is always set outside of the user creation code for two reasons.
The first time around the user is created but the push key isn't there yet (it arrives asynchronously)
Push is re-registered in every launch and refreshed, there is no reason to update the entire object for that
23. @RequestMapping(method = RequestMethod.GET,value = "/setPushToken")
public @ResponseBody String updatePushToken(
@RequestParam(name="token", required = true) String token,
@RequestParam(name="pushToken", required = true) String
pushToken) {
users.updatePushToken(token, pushToken);
return "OK";
}
UserWebservice
The UserWebservice class needs to mirror these changes obviously...
There isn't much here we just added a new setPushToken URL and we accept this update.
24. public class LocationService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Autowired
private WaypointRepository waypoints;
public void updateUserLocation(String token,double lat,double lon,float dir) {
List<User> us = users.findByAuthToken(token);
User u = us.get(0);
u.setLatitude(lat);
u.setLongitude(lat);
u.setDirection(dir);
users.save(u);
if(u.isDriver() && u.getAssignedUser() != null) {
List<Ride> r = rides.findByNotFinishedUser(u.getId());
if(r != null && !r.isEmpty()) {
Ride ride = r.get(0);
if(ride.isStarted() && !ride.isFinished()) {
Set<Waypoint> route = ride.getRoute();
Waypoint newPosition = new Waypoint(
System.currentTimeMillis(), lat, lon, dir);
waypoints.save(newPosition);
route.add(newPosition);
ride.setRoute(route);
rides.save(ride);
LocationService
The LocationService needs a bit more work.
Every time we update a users location we check if he's a driver on a ride
25. public class LocationService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Autowired
private WaypointRepository waypoints;
public void updateUserLocation(String token,double lat,double lon,float dir) {
List<User> us = users.findByAuthToken(token);
User u = us.get(0);
u.setLatitude(lat);
u.setLongitude(lat);
u.setDirection(dir);
users.save(u);
if(u.isDriver() && u.getAssignedUser() != null) {
List<Ride> r = rides.findByNotFinishedUser(u.getId());
if(r != null && !r.isEmpty()) {
Ride ride = r.get(0);
if(ride.isStarted() && !ride.isFinished()) {
Set<Waypoint> route = ride.getRoute();
Waypoint newPosition = new Waypoint(
System.currentTimeMillis(), lat, lon, dir);
waypoints.save(newPosition);
route.add(newPosition);
ride.setRoute(route);
rides.save(ride);
LocationService
Assuming we have a Ride object we check if this is currently an ongoing ride that wasn't finished
26. public class LocationService {
@Autowired
private UserRepository users;
@Autowired
private RideRepository rides;
@Autowired
private WaypointRepository waypoints;
public void updateUserLocation(String token,double lat,double lon,float dir) {
List<User> us = users.findByAuthToken(token);
User u = us.get(0);
u.setLatitude(lat);
u.setLongitude(lat);
u.setDirection(dir);
users.save(u);
if(u.isDriver() && u.getAssignedUser() != null) {
List<Ride> r = rides.findByNotFinishedUser(u.getId());
if(r != null && !r.isEmpty()) {
Ride ride = r.get(0);
if(ride.isStarted() && !ride.isFinished()) {
Set<Waypoint> route = ride.getRoute();
Waypoint newPosition = new Waypoint(
System.currentTimeMillis(), lat, lon, dir);
waypoints.save(newPosition);
route.add(newPosition);
ride.setRoute(route);
rides.save(ride);
LocationService
If so we add a waypoint to the ride and update it so we can later on inspect the path of the Ride.
This pretty much tracks rides seamlessly. If we wanted to be really smart we could detect the driver and user position to detect them traveling together and automatically
handle the ride. There are obviously problems with this as it means a user can't order a cab for someone else but it might be an interesting feature since we have two
close data points…