Merge branch 'interface' of AP-CT/Parkmanne into master

This commit is contained in:
Sagar Ramsaransing 2019-07-06 16:33:18 +00:00 committed by Gitea
commit f5c18d27f3
15 changed files with 196 additions and 66 deletions

View File

@ -25,6 +25,8 @@ add_executable(park
headers/Park_time.h headers/Park_time.h
Query.cpp Query.cpp
headers/Query.h headers/Query.h
Interface.cpp
headers/Interface.h
) )

View File

@ -1,21 +1,20 @@
#include "headers/Customer.h" #include "headers/Customer.h"
// constructors // constructors
Customer::Customer(string name_, string password_, Verhicle_type verhicle_) Customer::Customer(string name_, string password_, Vehicle_type vehicle_)
: name{name_}, verhicle{verhicle_}, password{hash_password(password_)} { : name{name_}, vehicle{vehicle_}, password{hash_password(password_)} {
id = auto_increment_db() + 1; id = auto_increment_db() + 1;
save_db(); save_db();
} }
Customer::Customer(int id_, string name_, string password_, Customer::Customer(int id_, string name_, string password_,
Verhicle_type verhicle_, vector<Park_time> instances) Vehicle_type vehicle_, vector<Park_time> instances)
:id{id_}, : id{id_},
name{name_}, name{name_},
password{password_}, password{password_},
verhicle{verhicle_}, vehicle{vehicle_},
park_instances{instances} {} park_instances{instances} {}
// clock in/out methods // clock in/out methods
// ==================================================================================== // ====================================================================================
/* /*
@ -31,6 +30,24 @@ void Customer::clock_out(int s_id) {
park_instances[park_instances.size() - 1].clock_out(id, s_id); park_instances[park_instances.size() - 1].clock_out(id, s_id);
} }
bool Customer::parked() {
if (!park_instances.size()){
return false;
}
if ((park_instances[park_instances.size() - 1].duration)) {
// if duration of the last parktime == 0, meaning
// that the customer has not clocked out
return false;
}
else {
return true;
}
}
int Customer::parked_at(){
return park_instances[park_instances.size() - 1].spot_id;
}
// report gen // report gen
void Customer::gen_monthly() { void Customer::gen_monthly() {
cout << "NAME: " << name << "\n"; cout << "NAME: " << name << "\n";
@ -49,7 +66,7 @@ void Customer::gen_monthly() {
void Customer::save_db() { void Customer::save_db() {
string statement{"insert into Customer values (, '', '', );"}; string statement{"insert into Customer values (, '', '', );"};
// after ( = 28) // after ( = 28)
statement.insert(38, to_string(int(verhicle))); statement.insert(38, to_string(int(vehicle)));
statement.insert(36, password); statement.insert(36, password);
statement.insert(32, name); statement.insert(32, name);
statement.insert(29, to_string(id)); statement.insert(29, to_string(id));
@ -83,5 +100,3 @@ int Customer::auto_increment_db() {
max_id.reset(); max_id.reset();
return id; return id;
} }

91
Interface.cpp Normal file
View File

@ -0,0 +1,91 @@
#include "headers/Interface.h"
// I added it to pass spots, because the parking options need it to check where
// is free parking_spots is declared in main, and if i declare it
void interface(vector<Park_spot>& spots) {
int selector;
cout << "\nHello and welcome to the parking spot! Please select a suitable "
"option:";
cout << "\n[1]Log in as member";
cout << "\n[2]Log in as administrator";
cin >> selector;
switch (selector) {
case 1:
interface_member(spots);
case 2:
interface_admin(spots);
}
}
void interface_member(vector<Park_spot>& spots) {
int id;
string password;
cout << "\nPlease input id:";
cin >> id;
Customer c = query_customer_with_id(id);
cout << "\nPlease input password:";
cin >> password;
while (!(verify_password(c.password, password))) {
cout << "ERROR: wrong password. Please retype your password \n";
cin >> password;
}
cout << "Logged in succesfully\n";
cout << "select an option\n [1] Parking options\n[2]other";
int option;
cin >> option;
switch (option) {
case 1: {
park(c, spots);
}
case 2: {
// other thing you want to add
break;
}
default:
break;
}
}
void interface_admin(vector<Park_spot>& spots) {}
// --------- individual things.
void park(Customer& c, vector<Park_spot>& spots) {
cout << "You have selected parking option";
if (!(c.parked())) {
cout << "The following spots[which can fit your vehicle] are "
"available: ";
for (Park_spot i : spots) {
if (i.v_type == c.vehicle) {
cout << i.id << ", ";
}
}
cout << "where do you want to park?";
int parkid;
cin >> parkid;
for (Park_spot& i : spots) {
if (i.id == parkid) {
i.clock(c);
cout << "You have parked sucessfully";
}
}
} else {
cout
<< "You are parked at spot " << c.parked_at()
<< ", do you want to clock out?\n enter [1] for yes and [0] for no";
int answer = 0;
cin >> answer;
if (answer) {
query_parkspot_with_id(c.parked_at(), spots).clock(c);
cout << "You have sucessfully clocked out.";
} else {
cout << "OK, have a nice day";
}
}
}

View File

@ -2,14 +2,15 @@
// constructors // constructors
Park_spot::Park_spot() Park_spot::Park_spot(Vehicle_type v_type_)
: parked_customer{0}, id{auto_increment_db() + 1}, taken{false} { : parked_customer{0}, id{auto_increment_db() + 1}, taken{false}, v_type{v_type_} {
save_db(); save_db();
} }
Park_spot::Park_spot(int id_, bool taken_, int parked) Park_spot::Park_spot(int id_, bool taken_, int parked,Vehicle_type v_type_)
: parked_customer{parked}, : parked_customer{parked},
id{id_}, id{id_},
v_type{v_type_},
taken{taken_} // TODO: think about how init parked? taken{taken_} // TODO: think about how init parked?
{} {}
@ -48,8 +49,9 @@ void Park_spot::update_db() {
void Park_spot::save_db() { void Park_spot::save_db() {
//(int id, bool taken, int customer_id) //(int id, bool taken, int customer_id)
string statement{"insert into Park_spot values ( , , );"}; string statement{"insert into Park_spot values ( , , , );"};
// after ( = 28) // after ( = 28)
statement.insert(36, to_string(int(v_type)));
statement.insert(34, "NULL"); statement.insert(34, "NULL");
statement.insert(32, "0"); statement.insert(32, "0");
statement.insert(30, to_string(id)); statement.insert(30, to_string(id));

View File

@ -112,4 +112,18 @@ int Park_time::auto_increment_db() {
id = max_id.getColumn(0); id = max_id.getColumn(0);
max_id.reset(); max_id.reset();
return id; return id;
}
//------------------ test function to help test this
void Wait(int sec)
{
/*
a wait function where 1 sec represents 1 hour irl. It has been used for testing
purposes mostly. TODO: Needs to be removed at completion of project, or seperated in a test
cpp/header
*/
std::this_thread::sleep_for(seconds{sec});
} }

View File

@ -38,16 +38,16 @@ vector<Customer> query_customer_with_name(string name) {
vector<Customer> result; vector<Customer> result;
SQLite::Statement query( SQLite::Statement query(
data::db, data::db,
"SELECT id, name, password, verhicle FROM Customer WHERE name = ?;"); "SELECT id, name, password, vehicle FROM Customer WHERE name = ?;");
query.bind(1, name); query.bind(1, name);
while (query.executeStep()) { while (query.executeStep()) {
int id = query.getColumn(0); int id = query.getColumn(0);
string name_ = query.getColumn(1); string name_ = query.getColumn(1);
string password = query.getColumn(2); string password = query.getColumn(2);
int verhicle = query.getColumn(3); // cast to verhicle int vehicle = query.getColumn(3); // cast to vehicle
vector<Park_time> park_instances = query_parktimes_for_customer(id); vector<Park_time> park_instances = query_parktimes_for_customer(id);
result.push_back(Customer{ result.push_back(Customer{
id, name_, password, Verhicle_type(verhicle), park_instances}); id, name_, password, Vehicle_type(vehicle), park_instances});
} }
return result; return result;
} }
@ -65,16 +65,26 @@ Customer query_customer_with_id(int id) {
while (query.executeStep()) { while (query.executeStep()) {
string name = query.getColumn(1); string name = query.getColumn(1);
string password = query.getColumn(2); string password = query.getColumn(2);
int verhicle = query.getColumn(3); // cast to verhicle int vehicle = query.getColumn(3); // cast to vehicle
vector<Park_time> park_instances = query_parktimes_for_customer(id); vector<Park_time> park_instances = query_parktimes_for_customer(id);
Customer result{ Customer result{
id, name, password, Verhicle_type(verhicle), park_instances}; id, name, password, Vehicle_type(vehicle), park_instances};
// DEBUG // DEBUG
// cout << "{" << result.id << "," <<result.password <<"," << int(verhicle) << "}\n"; // cout << "{" << result.id << "," <<result.password <<"," << int(vehicle) << "}\n";
return result; return result;
} }
} }
//-------------------------------
Park_spot query_parkspot_with_id(int id, vector<Park_spot>& parkspots){
for (Park_spot& i : parkspots){
if (i.id == id){
return i;
}
}
}
// -------------- paroking spots // -------------- paroking spots

View File

@ -20,11 +20,11 @@ SQLite::Database start_db() {
//sql syntax is surprisingly readable. //sql syntax is surprisingly readable.
db.exec( db.exec(
"create table if not exists Customer (id integer primary key, name " "create table if not exists Customer (id integer primary key, name "
"text, password text, verhicle int)"); "text, password text, vehicle int)");
// getting errors when using bool, so i used an int instead. // getting errors when using bool, so i used an int instead.
db.exec( db.exec(
"create table if not exists Park_spot (id integer primary key, taken " "create table if not exists Park_spot (id integer primary key, taken "
"int, customer_id int)"); "int, customer_id int, vehicle_type int)");
db.exec( db.exec(
"create table if not exists Park_time (id integer primary key, " "create table if not exists Park_time (id integer primary key, "
"customer_id int, spot_id int, start int, end int, duration int)"); "customer_id int, spot_id int, start int, end int, duration int)");

View File

@ -11,12 +11,12 @@ using std::vector;
/* /*
enum classes make it easy to represent categories. enum classes make it easy to represent categories.
So you can use something like Verhicle_type::car instead of 2. but under the So you can use something like Vehicle_type::car instead of 2. but under the
hood, it's still an int. This is here so you won't have to have global variables hood, it's still an int. This is here so you won't have to have global variables
for these categories, or worse, use magic numbers in the code. for these categories, or worse, use magic numbers in the code.
*/ */
enum class Verhicle_type { bike = 1, small_car = 2, suv = 3, pickup = 4 }; enum class Vehicle_type { bike = 1, small_car = 2, suv = 3, pickup = 4 };
/* /*
Customer constructors do the same stuff as all the other constructors. Customer constructors do the same stuff as all the other constructors.
@ -38,17 +38,19 @@ class Customer {
int id; int id;
string name; string name;
string password; string password;
Customer(string name_, string password_, Verhicle_type verhicle_); Customer(string name_, string password_, Vehicle_type vehicle_);
Customer(int id_, string name_, string password_, Verhicle_type verhicle_, Customer(int id_, string name_, string password_, Vehicle_type vehicle_,
vector<Park_time> instances); vector<Park_time> instances);
void clock_in(int s_id); void clock_in(int s_id);
void clock_out(int s_id); void clock_out(int s_id);
bool parked();
int parked_at();
void update_db(); void update_db();
void delete_db(); void delete_db();
void gen_monthly(); void gen_monthly();
Verhicle_type verhicle; Vehicle_type vehicle;
private: private:
vector<Park_time> park_instances; vector<Park_time> park_instances;

12
headers/Interface.h Normal file
View File

@ -0,0 +1,12 @@
#include "Query.h"
using std::cin;
void interface(vector<Park_spot>& spots);
void interface_member(vector<Park_spot>& spots);
void interface_admin(vector<Park_spot>& spots);
void park(Customer& c, vector<Park_spot>& spots);

View File

@ -18,8 +18,10 @@ class Park_spot {
int id; int id;
bool taken; bool taken;
int parked_customer; int parked_customer;
Park_spot(); Vehicle_type v_type;
Park_spot(int id_, bool taken_, int parked);
Park_spot(Vehicle_type v_type_);
Park_spot(int id_, bool taken_, int parked, Vehicle_type v_type_);
void clock(Customer& c_customer); void clock(Customer& c_customer);
private: private:

View File

@ -5,6 +5,7 @@
#include "data.h" #include "data.h"
#include <chrono> #include <chrono>
#include <thread>
#include <ctime> #include <ctime>
#include <iostream> #include <iostream>
#include <string> #include <string>
@ -63,4 +64,8 @@ class Park_time {
int start_to_int(); // helper int start_to_int(); // helper
}; };
//test funciton
void Wait(int sec);
#endif // Park_time #endif // Park_time

View File

@ -57,4 +57,7 @@ Customer query_customer_with_id(int id);
vector<Park_spot> populate_spots(); vector<Park_spot> populate_spots();
Park_spot query_parkspot_with_id(int id, vector<Park_spot>& parkspots);
#endif // CUSTOMER_H #endif // CUSTOMER_H

View File

@ -1,9 +1,7 @@
#include "headers/Query.h" #include "headers/Interface.h"
#include <thread>
using namespace std::chrono;
/* /*
Code structure is like this: Code structure is like this:
@ -44,43 +42,18 @@ headers. Explanations of how the member functions work(Or how I intended for
them to work) are in the respective .cpp files. void Wait(int sec) them to work) are in the respective .cpp files. void Wait(int sec)
*/ */
void Wait(int sec)
{
/*
a wait function where 1 sec represents 1 hour irl. It has been used for testing
purposes mostly.
TODO: Needs to be removed at completion of project, or seperated in a test
cpp/header
*/
std::this_thread::sleep_for(seconds{sec});
}
static vector<Park_spot> parking_spots = populate_spots(); static vector<Park_spot> parking_spots = populate_spots();
// this queries the db for all the saved parking_spots and initializes them // this queries the db for all the saved parking_spots and initializes them
static vector<Customer> park_customers; static vector<Customer> park_customers;
/*
This was meant for an older implementation. park_time objects used to store
pointers to customers and in order to not get dangling pointers(dangerous!) I
had to have a way to store the customers the pointer pointed to so they didn't
get destroyed prematurely(I could've used the lower-level, more dangerous new,
or worse, malloc, but that's ugly).
For now, it's just here in case you want an easy way to store customers.
*/
int main() { int main() {
Customer sagar = query_customer_with_name("stefan udit")[0]; // state of db:
Customer sagar1 = query_customer_with_id(2); // er zijn 10 parkspots, 5 met biketype en 5 met pickup type
cout << sagar.id << "," << sagar.name << "," << sagar.password << "\n"; // er is een customer met id 1(testcustomer) met password "password"
cout << sagar1.id << "," << sagar1.name << "," << sagar1.password;
cout << parking_spots.size(); interface(parking_spots);
for (auto i : parking_spots) {
cout << "\n" << i.id << "," << i.parked_customer;
}
populate_spots();
} }
/* /*
@ -91,13 +64,12 @@ concurrency issue. Do not move this.
vector<Park_spot> populate_spots() { vector<Park_spot> populate_spots() {
vector<Park_spot> spots; vector<Park_spot> spots;
SQLite::Statement query(data::db, "SELECT * FROM Park_spot WHERE id > 0;"); SQLite::Statement query(data::db, "SELECT * FROM Park_spot WHERE id > 0;");
// query.bind(1, 2);
while (query.executeStep()) { while (query.executeStep()) {
int id = query.getColumn(0); int id = query.getColumn(0);
int taken = query.getColumn(1); int taken = query.getColumn(1);
int cid = query.getColumn(2); int cid = query.getColumn(2);
// park_customers.push_back(query_customer_with_id(cid)); Vehicle_type vtype = Vehicle_type(int(query.getColumn(3)));
spots.push_back({id, taken, cid}); spots.push_back({id, taken, cid, vtype});
} }
return spots; return spots;
} }

Binary file not shown.

BIN
test.db3

Binary file not shown.