 Advertisement.h
1 #ifndef ADVERTISEMENT_H
2 #define ADVERTISEMENT_H
3
4 #include <queue>
5 #include <iostream>
6 #include <string>
7 #include "Date.h"
8 #include "Bid.h"
9
10 using namespace std;
11
12 class Advertisement;
13
14 istream &operator>>(istream &stream, Advertisement &a);
15
16 class Advertisement {
17
18 private:
19
20 int number;
21 int quantity;
22 string title;
23 string seller_email;
24 string body;
25
26 Date start;
27 Date close;
28 priority_queue<Bid> bids;
29
30 public:
31
32 Advertisement(void);
33 Advertisement(const Advertisement &a);
34 Advertisement (string title, string seller_email, string body,
35 Date start, Date close, int quantity);
36
37 virtual void setStart (const Date &start);
38 virtual void setClose (const Date &close);
39 virtual void setTitle (string title);
40 virtual void setBody (string body);
41 virtual void setNumber (int number);
42 virtual void setEmail (string email);
43 virtual void setQuantity (int quantity);
44
45 virtual Date getStart () const;
46 virtual Date getClose () const;
47 virtual string getTitle() const;
48 virtual string getBody() const;
49 virtual string getEmail() const;
50 virtual int getNumber () const;
51 virtual int getQuantity() const;
52
53 virtual bool operator==(const Advertisement&) const;
54
55 virtual priority_queue<Bid>& getBids(void);
56 virtual vector<Bid> getTopDutchBids (void) const;
57
58 };
59
60 #endif
 Advertisement.cpp
1 #include "Advertisement.h"
2 Advertisement::Advertisement()
3 {
4 int number=0;
5 int quantity=0;
6 string title;
7 string seller_email;
8 string body;
9 Date start;
10 Date close;
11
12 }
13 Advertisement::Advertisement(const Advertisement &a)
14 {
15 this->body=a.getBody();
16 this->close=a.getClose();
17 this->number=a.getNumber();
18 this->quantity=a.getQuantity();
19 this->seller_email=a.getEmail();
20 this->start=a.getStart();
21 this->title=a.getTitle();
22 }
23 Advertisement::Advertisement (string title, string seller_email, string body,
24 Date start, Date close, int quantity)
25 {
26 this->title=title;
27 this->seller_email=seller_email;
28 this->body=body;
29 this->start=start;
30 this->close=close;
31 this->quantity=quantity;
32 }
33 void Advertisement::setStart(const Date &start)
34 {
35 this->start=start;
36 }
37 void Advertisement::setClose (const Date &close)
38 {
39 this->close=close;
40 }
41 void Advertisement::setTitle (string title)
42 {
43 this->title=title;
44 }
45 void Advertisement::setBody (string body)
46 {
47 this->body=body;
48 }
49 void Advertisement::setNumber (int number)
50 {
51 this->number=number;
52 }
53 void Advertisement::setEmail (string email)
54 {
55 this->seller_email=email;
56 }
57 void Advertisement::setQuantity (int quantity)
58 {
59 this->quantity=quantity;
60 }
61 Date Advertisement::getStart () const
62 {
63 return this->start;
64 }
65 Date Advertisement::getClose () const
66 {
67 return this->close;
68 }
69 string Advertisement::getTitle() const
70 {
71 return this->title;
72 }
73 string Advertisement::getBody() const
74 {
75 return this->body;
76 }
77 string Advertisement::getEmail() const
78 {
79 return this->seller_email;
80 }
81 int Advertisement::getNumber() const
82 {
83 return this->number;
84 }
85 int Advertisement::getQuantity() const
86 {
87 return this->quantity;
88 }
89 bool Advertisement::operator ==(const Advertisement &a) const
90 {
91 if(this->number==a.getNumber()&&this->quantity==a.getQuantity()&&this->title==a.getTitle()&&this->seller_email==a.getEmail()&&this->body==a.getBody()&&this->getStart()==a.getStart()&&this->getClose()==a.getClose())
92 {
93 return true;
94 }
95 else
96 {
97 return false;
98 }
99 }
100 istream &operator>>(istream &stream, Advertisement &a)
101 {
102 int number=0;
103 int quantity=0;
104 string title;
105 string seller_email;
106 string body;
107 Date start;
108 Date close;
109
110 stream>>title;
111 stream>>seller_email;
112 stream>>quantity;
113 stream>>start;
114 stream>>close;
115 stream>>body;
116 a.setTitle(title);
117 a.setEmail(seller_email);
118 a.setQuantity(quantity);
119 a.setStart(start);
120 a.setClose(close);
121 a.setBody(body);
122 return stream;
123 }
124 priority_queue<Bid>& Advertisement::getBids(void)
125 {
126 return this->bids;
127 }
128 //maybe some troubles
129 vector<Bid> Advertisement::getTopDutchBids(void) const
130 {
131 int Aq=this->quantity;
132 vector<Bid> a;
133 int count=0;
134 priority_queue<Bid> test;
135 test=this->bids;
136 while(Aq>0&&!test.empty())
137 {
138
139 if(Aq>test.top().getQuantity())
140 {
141 Aq=Aq-test.top().getQuantity();
142 a.push_back(test.top());
143 test.pop();
144 }
145 else
146 {
147 if(Aq<test.top().getQuantity())
148 {
149 test.top().setQuantity(Aq);
150 a.push_back(test.top());
151 test.pop();
152 Aq=0;
153 break;
154 }
155 break;
156 }
157 }
158 return a;
159 }
 Bid.h
1 #ifndef BID_H
2 #define BID_H
3
4 #include <iostream>
5 #include <string>
6 #include "Date.h"
7
8 using namespace std;
9
10 class Bid;
11
12 istream &operator>>(istream &stream, Bid &b);
13
14 class Bid {
15
16 private:
17
18 string email;
19 float amount;
20 int quantity;
21 Date date;
22
23 public:
24
25 Bid(void);
26 Bid(const Bid &b);
27 Bid (string email, float amount, int quantity, Date date);
28
29 virtual string getEmail () const ;
30 virtual float getAmount () const;
31 virtual int getQuantity () const;
32 virtual Date getDate () const;
33
34 virtual void setEmail(const string&);
35 virtual void setAmount(const float&);
36 virtual void setQuantity(const int&);
37 virtual void setDate(const Date&);
38
39 virtual bool operator< (const Bid &rhs) const;
40 virtual bool operator== (const Bid &rhs) const;
41 };
42
43 #endif
 Bid.cpp
1 #include"Bid.h"
2 Bid::Bid()
3 {
4 this->email;
5 this->amount=0;
6 this->quantity=0;
7 this->date;
8 }
9 Bid::Bid(string email, float amount, int quantity, Date date)
10 {
11 this->email=email;
12 this->amount=amount;
13 this->quantity=quantity;
14 this->date=date;
15 }
16 Bid::Bid(const Bid &b)
17 {
18 this->email=b.getEmail();
19 this->amount=b.getAmount();
20 this->quantity=b.getQuantity();
21 this->date=b.getDate();
22
23 }
24 string Bid::getEmail() const
25 {
26 return this->email;
27 }
28 float Bid::getAmount() const
29 {
30 return this->amount;
31 }
32 int Bid::getQuantity() const
33 {
34 return this->quantity;
35 }
36 Date Bid::getDate() const
37 {
38 return this->date;
39 }
40 void Bid::setEmail(const string &email)
41 {
42 this->email=email;
43 }
44 void Bid::setAmount(const float &amount)
45 {
46 this->amount=amount;
47 }
48 void Bid::setQuantity(const int &quantity)
49 {
50 this->quantity=quantity;
51 }
52 void Bid::setDate(const Date &date)
53 {
54 this->date=date;
55 }
56 bool Bid::operator< (const Bid &rhs) const
57 {
58 if(this->amount<rhs.getAmount())
59 return true;
60 else
61 return false;
62 }
63 bool Bid::operator==(const Bid &rhs) const
64 {
65 if(this->amount==rhs.getAmount())
66 return true;
67 else
68 return false;
69
70
71 }
72 istream &operator>>(istream &stream, Bid &b)
73 {
74 string email;
75 float amount;
76 int quantity;
77 Date date;
78 stream>>email;
79 stream>>amount;
80 stream>>quantity;
81 stream>>date;
82 b.setAmount(amount);
83 b.setEmail(email);
84 b.setQuantity(quantity);
85 b.setDate(date);
86 return stream;
87
88
89 }
 bidhistory.h
1 #ifndef BIDHISTORY_H
2 #define BIDHISTORY_H
3
4 #include <sstream>
5
6 using namespace std;
7
8 void displayBidHistory(ostringstream &oss, Advertisement* ad);
9
10 #endif
 bidhistory.cpp
1 #include "main.h"
2 #include "bidhistory.h"
3
4 using namespace std;
5
6 void displayBidHistory(ostringstream &oss, Advertisement* ad)
7 {
8 priority_queue<Bid> bids=ad->getBids();
9 Client *client=users[ad->getEmail()];
10 int count=0;
11 oss<<"Advertisement Information"<<"<br><br>"<<endl;
12 oss <<"First name:"<<client->getFname()<<"<br>"<< endl;
13 oss<<"Last name:"<<client->getLname()<<"<br>"<<endl;
14 oss <<"Quantity:"<<ad->getQuantity()<<"<br>"<<endl;
15 oss<<"Total number of bids:"<<ad->getBids().size()<<"<br>"<<endl;
16 if(ad->getQuantity()==1)
17 {
18 if(!bids.empty())
19 {
20 Bid b=bids.top();
21
22 oss<<"highest bid"<<"<br>"<<endl;
23 oss<<"bidder's email of highest bid:"<<b.getEmail()<<"<br>"<<endl;
24 oss<<"Dollar amount:"<<b.getAmount()<<"<br>"<<endl;
25 }
26 }
27 if(ad->getQuantity()>1)
28 {
29 vector<Bid> b=ad->getTopDutchBids();
30 oss<<"winning bids"<<"<br>"<<endl;
31 for(vector<Bid> ::iterator aaa=b.begin();aaa!=b.end();aaa++)
32 {
33 oss<<"-------------------------------------------------<br>";
34 oss<<"bidder's email address:"<<(*aaa).getEmail()<<"<br>";
35 oss<<"dollar amount of the bid:"<<(*aaa).getAmount()<<"<br>";
36 int size=bids.size();
37 int qq=0;
38 for(int i =0;i<size;i++)
39 {
40 Bid rhs=bids.top();
41 if(rhs.getEmail()==(*aaa).getEmail())
42 {
43 qq=qq+rhs.getQuantity();
44 }
45 bids.pop();
46 }
47 oss<<"the number of items bid on:"<<qq<<"<br>";
48 oss<<"The number of items winning: "<<(*aaa).getQuantity()<<"<br>";
49 count=count+(*aaa).getQuantity();
50 oss<<"-------------------------------------------------<br>";
51 }
52 oss<<"<br><br>";
53 oss<<"advertisement that have not been bid on:"<<ad->getQuantity()-count<<"<br>";
54 }
55 }
 buildbidpage.h
1 #ifndef BUILDBIDPAGE_H
2 #define BUILDBIDPAGE_H
3
4 #include <sstream>
5
6 using namespace std;
7
8 void buildbidpage (ostringstream &oss, int port, int number);
9 void displayBidForm(ostringstream &oss, struct in_addr ip, int port, int number);
10
11 #define CLASSIFIED_CGI "classified.cgi"
12
13 #endif
 buildbidpage.cpp
1 #include <sstream>
2 #include <winsock2.h>
3 #include <ws2tcpip.h>
4 #include <signal.h>
5 #include <cstdio>
6
7 #include "main.h"
8 #include "buildpage.h"
9 #include "buildbidpage.h"
10 #include "bidhistory.h"
11 #include "Client.h"
12 #include "Advertisement.h"
13 #include "Listing.h"
14 #include "Group.h"
15
16 using namespace std;
17
18 void buildbidpage (ostringstream &oss, int port, int number) {
19
20 in_addr ip;
21 ip = getIP();
22
23 displayPageHeader(oss);
24
25 Advertisement *ad = NULL;
26 ad = advertisements[number];
27
28 oss << "<table border=0 width=100%>" << endl;
29 oss << "<tr><td valign=top width=50%>" << endl;
30 oss << "<b>" << ad->getTitle() << "</b><br>" << endl;
31 displayBidHistory(oss, ad);
32
33 oss << "<td valign=top>" << endl;
34 displayBidForm(oss, ip, port, number);
35 oss << "</tr></table>" << endl;
36
37 oss << "</body>" << endl;
38 oss << "</html>" << endl;
39 }
40
41 void displayBidForm(ostringstream &oss, struct in_addr ip, int port, int number) {
42
43 Advertisement *ad = NULL;
44 ad = advertisements[number];
45
46 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
47 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
48 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
49 oss << "<INPUT NAME=email TYPE=hidden VALUE=" << active_user << ">" << endl;
50 oss << "<INPUT NAME=number TYPE=hidden VALUE=" << number << ">" << endl;
51
52 oss << "<b><center>Place Bid</center></b><br>" << endl;
53 oss << "<table border=0 width=100%>" << endl;
54 oss << "<tr><td align=right>Bid amount:" << endl;
55
56 float high_bid = 0;
57 if (ad->getBids().size() > 0) {
58 high_bid = ad->getBids().top().getAmount();
59 }
60 oss << "<td><INPUT NAME=amount TYPE=text SIZE=5 VALUE="
61 << high_bid + 1 << "></tr>" << endl;
62
63 oss << "<tr><td align=right>Quantity:" << endl;
64 if (ad->getQuantity() > 1) {
65 oss << "<td><INPUT NAME=quantity SIZE=5 TYPE=text VALUE=1></tr>" << endl;
66 }
67 else {
68 oss << "<td><INPUT NAME=quantity TYPE=hidden VALUE=1>1</tr>" << endl;
69 }
70
71 oss << "<tr><td align=center colspan=2>" << endl;
72 oss << "<INPUT NAME=COMMAND TYPE=submit VALUE=\"Submit bid\">" << endl;
73 oss << "</FORM>" << "</tr></table>" << endl;
74 }
 buildpage.h
1 #ifndef BUILDPAGE_H
2 #define BUILDPAGE_H
3
4 #include <sstream>
5 #include "Listing.h"
6
7 using namespace std;
8
9 in_addr getIP(void);
10 void displayPageHeader(ostringstream &oss);
11
12 void displaySortFind (ostringstream &oss, struct in_addr ip, int port);
13 void displayCategoryFilter(ostringstream &oss, struct in_addr ip, int port);
14 void displayPostItem (ostringstream &oss, struct in_addr ip, int port);
15 void displayRegister (ostringstream &oss, struct in_addr ip, int port);
16 void displayLogin (ostringstream &oss, struct in_addr ip, int port);
17 void displayLogout (ostringstream &oss, struct in_addr ip, int port);
18 void displayControlPanel (ostringstream &oss, struct in_addr ip, int port);
19 void displayAdvertisement (ostringstream &oss, Advertisement* ad, struct in_addr ip,
20 int port);
21 void displayBidButton(ostringstream &oss, Advertisement* ad, struct in_addr ip,
22 int port);
23
24 void buildpage (ostringstream &oss, int port, Listing::iterator start,
25 Listing::iterator finish);
26
27 #define CLASSIFIED_CGI "classified.cgi"
28
29 #endif
 buildpage.cpp
1 #include <sstream>
2 #include <winsock2.h>
3 #include <ws2tcpip.h>
4 #include <signal.h>
5 #include <stdio.h>
6 #include <ctime>
7
8 #include "main.h"
9 #include "buildpage.h"
10 #include "Client.h"
11 #include "Advertisement.h"
12 #include "Listing.h"
13 #include "Group.h"
14
15 using namespace std;
16
17 void buildpage (ostringstream &oss, int port, Listing::iterator start,
18 Listing::iterator finish) {
19
20 in_addr ip;
21 ip = getIP();
22
23 displayPageHeader(oss);
24
25 oss << "<TABLE width=100% cellpadding=3 cellspacing=3>" << endl;
26 oss << "<TR>" << endl;
27 oss << "<td width=50% class=advertisement>" << endl;
28 displaySortFind(oss, ip, port);
29 displayCategoryFilter(oss, ip, port);
30
31 oss << "<table width=100%>" << endl;
32 if (start == finish) {
33 oss << "<tr><td><b>No items</b></td></tr>" << endl;
34 }
35 else {
36 for (Listing::iterator it = start; it != finish; it++) {
37 oss << "<tr><td class=advertisement>" << endl;
38 displayAdvertisement (oss, *it, ip, port);
39 oss << "</td></tr>" << endl;
40 }
41 }
42 oss << "</table>";
43
44 oss << "<td class=controlpanel>" << endl;
45 displayControlPanel(oss, ip, port);
46 oss << "</td></tr>" << endl;
47
48 // Page Footer
49 oss << "</TABLE>" << endl;
50 oss << "</BODY>" << endl;
51 oss << "</HTML>" << endl;
52
53 }
54
55 void displayPageHeader(ostringstream &oss) {
56
57 // HTTP Content-type header
58 oss << "Content-type: text/html" << "\r\n\r\n";
59
60 // Start generating the page
61 oss << "<HTML>" << endl;
62 oss << "<HEAD>" << endl;
63 oss << "<TITLE>" << endl;
64 oss << "iCarnegie Auctions" << endl;
65 oss << "</TITLE>" << endl;
66 oss << "<link rel=\"stylesheet\" type=\"text/css\" href=\"/auction.css\" />" << endl;
67 oss << "</HEAD>" << endl;
68 oss << endl;
69 oss << "<BODY>" << endl;
70 oss << "<CENTER><H2>iCarnegie Auctions</H2></CENTER>" << endl;
71 }
72
73 void displayPostItem (ostringstream &oss, struct in_addr ip, int port) {
74
75 oss << "<B><CENTER>" << "Post an Ad" << "</CENTER></B><BR>" << endl;
76
77 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
78 oss << "<table border=0 width=100%>" << endl;
79 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
80 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
81 oss << "<INPUT NAME=email TYPE=hidden VALUE=" << active_user << ">" << endl;
82 oss << "<tr><td align=right>Title:<td>" << endl;
83 oss << "<INPUT NAME=title TYPE=text WIDTH=20 MAXWIDTH=20></tr>" << endl;
84
85 oss << "<tr><td align=right>Category:<td>" << endl;
86 oss << "<SELECT NAME=category>" << endl;
87
88 for (Categories::iterator it = categories.begin();
89 it != categories.end();
90 it++) {
91
92 oss << "<OPTION value=\"" << (*it)->getNumber() << "\">"
93 << (*it)->getName() << "</OPTION>" << endl;
94 }
95 oss << "</SELECT></tr>" << endl;
96
97 oss << "<tr><td align=right>Length:<td><SELECT NAME=days>" << endl;
98 oss << "<OPTION value=3>3 days" << endl;
99 oss << "<OPTION SELECTED value=5>5 days" << endl;
100 oss << "<OPTION value=7>7 days" << endl;
101 oss << "</SELECT></tr>" << endl;
102 oss << "<tr><td align=right>Quantity:<td>" << endl;
103 oss << "<INPUT NAME=quantity VALUE=1 TYPE=text SIZE=5 MAXLENGTH=4></tr>" << endl;
104 oss << "<tr><td valign=top align=right>Description:<td>" << endl;
105 oss << "<TEXTAREA NAME=body COLS=20 ROWS=4>" << endl;
106 oss << "</TEXTAREA></tr>" << endl;
107 oss << "<tr><td align=center colspan=2><INPUT NAME=COMMAND VALUE=Add TYPE=submit></tr>" << endl;
108 oss << "</FORM></table>" << endl;
109 }
110
111 void displaySortFind (ostringstream &oss, struct in_addr ip, int port) {
112
113 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
114 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
115 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
116 oss << "<INPUT NAME=COMMAND VALUE=\"Sort\" TYPE=submit>" << endl;
117 oss << " " << endl;
118 oss << "<SELECT NAME=field>" << endl;
119 oss << "<OPTION value=\"close\">By close date" << endl;
120 oss << "<OPTION value=\"start\">By start date" << endl;
121 oss << "<OPTION value=\"email\">By seller email" << endl;
122 oss << "<OPTION value=\"quantity\">By quantity" << endl;
123 oss << "<OPTION value=\"highest\">By highest Bid" << endl;
124 oss << "<OPTION value=\"lowest\">By lowest Bid" << endl;
125 oss << "</SELECT>" << endl;
126 oss << " " << endl;
127 oss << "<INPUT NAME=COMMAND VALUE=\"Find\" TYPE=submit>" << endl;
128 oss << " " << endl;
129 oss << "<INPUT NAME=keyword TYPE=text SIZE=15 MAXLENGTH=20>" << endl;
130 oss << "</FORM>" << endl;
131 }
132
133 void displayCategoryAdd(ostringstream &oss, struct in_addr ip, int port) {
134
135 oss << "<B><CENTER>" << "Add Sub-Category" << "</CENTER></B><BR>" << endl;
136 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
137 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
138 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
139
140 oss << "<table width=100%><tr><td align=right>Parent category:<td>" << endl;
141 oss << "<SELECT NAME=parent>" << endl;
142
143 for (Categories::iterator it = categories.begin();
144 it != categories.end();
145 it++) {
146
147 oss << "<OPTION value=\"" << (*it)->getNumber() << "\">"
148 << (*it)->getName() << "</OPTION>" << endl;
149 }
150 oss << "</SELECT></tr>" << endl;
151
152 oss << "<tr><td align=right>New category:<td>" << endl;
153 oss << "<INPUT NAME=newcategory TYPE=text></tr>" << endl;
154 oss << "<tr><td colspan=2 align=center>" << endl;
155 oss << "<INPUT NAME=COMMAND TYPE=submit VALUE=\"Add subcategory\">" << endl;
156 oss << "</tr></table></FORM>" << endl;
157 }
158
159 void displayCategoryFilter(ostringstream &oss, struct in_addr ip, int port) {
160
161 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
162 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
163 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
164 oss << "Category: " << endl;
165 oss << "<SELECT NAME=category>" << endl;
166
167 for (Categories::iterator it = categories.begin();
168 it != categories.end();
169 it++) {
170 oss << "<OPTION value=\"" << (*it)->getNumber() << "\">"
171 << (*it)->getName() << "</OPTION>" << endl;
172 }
173 oss << "</SELECT>" << endl;
174
175 oss << "<INPUT NAME=COMMAND VALUE=\"Top Only\" TYPE=submit>" << endl;
176 oss << "<INPUT NAME=COMMAND VALUE=\"Recursive\" TYPE=submit>" << endl;
177 oss << "</FORM>" << endl;
178 }
179
180 void displayRegister (ostringstream &oss, struct in_addr ip, int port) {
181
182 oss << "<B><CENTER>Create Account</CENTER></B><BR>" << endl;
183 if (!create_verified) {
184 oss << "<FONT COLOR=red>Passwords didn't match.</FONT>" << endl;
185 create_verified = true;
186 }
187 oss << "<table width=100%>" << endl;
188 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
189 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
190 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
191 oss << "<tr><td align=right>Email:<td><INPUT NAME=email TYPE=text SIZE=20 MAXLENGTH=30></tr>"
192 << endl;
193 oss << "<tr><td align=right>Last name:<td><INPUT NAME=lname TYPE=text SIZE=20 MAXLENGTH=20></tr>"
194 << endl;
195 oss << "<tr><td align=right>First name:<td><INPUT NAME=fname TYPE=text SIZE=20 MAXLENGTH=20></tr>"
196 << endl;
197 oss << "<tr><td align=right>Password:<td><INPUT NAME=passwd TYPE=password SIZE=20 MAXLENGTH=60></tr>" << endl;
198 oss << "<tr><td align=right>Password (again):<td><INPUT NAME=passwd2 TYPE=password SIZE=20 MAXLENGTH=60></tr>" << endl;
199 oss << "<tr><td align=center colspan=2><INPUT NAME=COMMAND VALUE=\"Create\" TYPE=submit></tr>" << endl;
200 oss << "</FORM>" << endl;
201 }
202
203 void displayControlPanel (ostringstream &oss, struct in_addr ip, int port) {
204
205 // If someone is logged in
206 if ("" != active_user) {
207
208 displayLogout(oss, ip, port);
209 oss << "<hr>" << endl;
210
211 displayPostItem(oss, ip, port);
212 oss << "<hr>" << endl;
213
214 displayCategoryAdd(oss, ip, port);
215 }
216 else {
217
218 displayLogin(oss, ip, port);
219 oss << "<hr>" << endl;
220
221 displayRegister(oss, ip, port);
222 }
223 }
224
225 void displayLogout (ostringstream &oss, struct in_addr ip, int port) {
226
227 oss << "<center>" << endl;
228 oss << "Your userid: " << active_user << " " << endl;
229 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
230 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
231 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
232 oss << "<INPUT NAME=COMMAND VALUE=Logout TYPE=submit>" << endl;
233 oss << "</FORM></center>" << endl;
234 }
235
236 void displayLogin (ostringstream &oss, struct in_addr ip, int port) {
237
238 oss << "<center>" << endl;
239 if (login_failed) {
240 oss << "<b><FONT COLOR=red>Login failed.</FONT></b></br>" << endl;
241 login_failed = false;
242 }
243 else {
244 oss << "<b>Login</b></br>" << endl;
245 }
246 oss << "</center>" << endl;
247
248 oss << "<table border=0 width=100%>" << endl;
249 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
250 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
251 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
252 oss << "<tr><td align=right>Email:" << endl;
253 oss << "<td><INPUT NAME=email TYPE=text SIZE=12 MAXLENGTH=30></tr>" << endl;
254 oss << "<tr><td align=right>Password:" << endl;
255 oss << "<td><INPUT NAME=passwd TYPE=password SIZE=12 MAXWLENGTH=10></tr>" << endl;
256 oss << "<tr><td colspan=2 align=center>" << endl;
257 oss << "<INPUT NAME=COMMAND VALUE=\"Login\" TYPE=submit>" << endl;
258 oss << "</FORM></tr></table>" << endl;
259
260 }
261
262 void displayAdvertisement (ostringstream &oss, Advertisement* ad, struct in_addr ip,
263 int port) {
264
265 Client* seller = NULL;
266 seller = users[ad->getEmail()];
267
268 oss << "<table border=0 width=100%><tr><td align=center width=15%>" << endl;
269 if ("" != active_user) {
270 displayBidButton(oss, ad, ip, port);
271 }
272 else {
273 oss << " " << endl;
274 }
275 oss << "<td>" << endl;
276 oss << "<B>" << ad->getTitle() << "</B><br>" << endl;
277 oss << "Posted by: <A HREF=mailto:" << ad->getEmail() << ">";
278 oss << seller->getLname() << ", " << seller->getFname() << "</a><br>" << endl;
279 oss << "Posted: " << ad->getStart() << "<br>" << endl;
280 oss << "Closes: " << ad->getClose() << "<br>" << endl;
281 oss << "Quantity: " << ad->getQuantity() << "<br>" << endl;
282 oss << "Number of bids: " << ad->getBids().size() << "<br>" << endl;
283
284 if (ad->getBids().size() > 0) {
285 oss << "High bid: $" << ad->getBids().top().getAmount() << "<br>" << endl;
286 }
287
288 oss << ad->getBody() << endl;
289 oss << "</tr></table>" << endl;
290 }
291
292 void displayBidButton(ostringstream &oss, Advertisement* ad, struct in_addr ip,
293 int port) {
294
295 oss << "<FORM ACTION=" << CLASSIFIED_CGI << " METHOD=POST>" << endl;
296 oss << "<INPUT NAME=PORT TYPE=hidden VALUE=" << port << ">" << endl;
297 oss << "<INPUT NAME=IP TYPE=hidden VALUE=" << inet_ntoa(ip) << ">" << endl;
298 oss << "<INPUT NAME=email TYPE=hidden VALUE=" << active_user << ">" << endl;
299 oss << "<INPUT NAME=number VALUE=" << ad->getNumber() << " TYPE=hidden>" << endl;
300 oss << "<INPUT NAME=COMMAND VALUE=Bid TYPE=submit></FORM>" << endl;
301 }
302
303 in_addr getIP(void) {
304
305 // Find self for form parm
306 char hostname_str[256];
307 gethostname (hostname_str, 256);
308 hostent *he = gethostbyname (hostname_str);
309 in_addr ip;
310 memcpy (&ip.s_addr, he->h_addr_list[0], sizeof(ip.s_addr));
311
312 return ip;
313 }
 Categories.h
1 #ifndef CATEGORIES_H
2 #define CATEGORIES_H
3
4 #include <string>
5 #include <vector>
6
7 #include "Category.h"
8 #include "Listing.h"
9
10 using namespace std;
11
12 class Categories {
13
14 protected:
15 typedef vector<Category*> Container;
16
17 public:
18 typedef Container::iterator iterator;
19
20 protected:
21 Container objects;
22
23 public:
24 static const int TOP_LEVEL=0;
25 static const int NO_PARENT=0;
26
27 virtual Category* operator[](const int& number);
28 virtual void add(Category* ptr);
29
30 virtual iterator begin();
31 virtual iterator end();
32
33 };
34
35
36 #endif
 Categories.cpp
1 #include "Categories.h"
2 Category* Categories::operator[](const int& number)
3 {
4 for(vector<Category*>::iterator aa=objects.begin();aa!=objects.end();aa++)
5 {
6 if((*aa)->getNumber()==number)
7 {
8 return *aa;
9 }
10
11 }
12 return NULL;
13 }
14 void Categories::add(Category* ptr)
15 {
16 objects.push_back(ptr);
17 }
18 vector<Category*>::iterator Categories::begin()
19 {
20 return objects.begin();
21 }
22 vector<Category*>::iterator Categories::end()
23 {
24 return objects.end();
25 }
 Category.h
1 #ifndef CATEGORY_H
2 #define CATEGORY_H
3
4 #include <string>
5 #include <vector>
6
7 #include "Listing.h"
8
9 using namespace std;
10
11 class Category;
12
13 istream &operator>>(istream &stream, Category &c);
14
15 class Category {
16
17 public:
18 int number;
19 int parent;
20 string name;
21
22 vector<Category*> sub_categories;
23 vector<int> items;
24
25
26
27 Category(void);
28 Category(int parent, string name);
29
30 virtual int getNumber(void) const;
31 virtual int getParent(void) const;
32 virtual string getName(void) const;
33
34 virtual void setNumber(int);
35 virtual void setParent(int);
36 virtual void setName(string);
37
38 virtual void addSubCategory(Category*);
39 virtual void addItem(int);
40
41 virtual void findOfferings (Listing::iterator start,
42 Listing::iterator finish, Listing &matches);
43 virtual void findOfferingsRecursive (Listing::iterator start,
44 Listing::iterator finish, Listing &matches);
45
46 virtual vector<int>::iterator itemsBegin();
47 virtual vector<int>::iterator itemsEnd();
48 virtual vector<Category*>::iterator subCategoriesBegin();
49 virtual vector<Category*>::iterator subCategoriesEnd();
50
51 virtual bool operator==(const Category& rhs);
52
53 };
54
55 #endif
 Category.cpp
1 #include "Category.h"
2
3 Category::Category()
4 {
5 this->number=0;
6 this->parent=0;
7 this->name;
8
9 }
10 int Category::getNumber(void) const
11 {
12 return this->number;
13 }
14 int Category::getParent(void) const
15 {
16 return this->parent;
17 }
18 string Category::getName(void) const
19 {
20 return this->name;
21 }
22 void Category::setNumber(int a)
23 {
24 this->number=a;
25 }
26 void Category::setParent(int a)
27 {
28 this->parent=a;
29 }
30 void Category::setName(string a)
31 {
32 this->name=a;
33 }
34 Category::Category(int parent, string name)
35 {
36 this->parent=parent;
37 this->name=name;
38 }
39 vector<int>::iterator Category::itemsBegin()
40 {
41 return items.begin();
42 }
43 vector<int>::iterator Category::itemsEnd()
44 {
45 return items.end();
46 }
47 vector<Category*>::iterator Category::subCategoriesBegin()
48 {
49 return sub_categories.begin();
50 }
51 vector<Category*>::iterator Category::subCategoriesEnd()
52 {
53 return sub_categories.end();
54 }
55 void Category::addItem(int item)
56 {
57 items.push_back(item);
58 }
59 void Category::addSubCategory(Category* ptr)
60 {
61
62 sub_categories.push_back(ptr);
63
64
65 }
66 void Category::findOfferings(Listing::iterator start, Listing::iterator finish, Listing &matches)
67 {
68 Listing::iterator aa;
69
70 for(aa=start;aa!=finish;aa++)
71 {
72 matches.add(*aa);
73 }
74 }
75 void Category::findOfferingsRecursive (Listing::iterator start, Listing::iterator finish, Listing &matches)
76 {
77 findOfferings(start,finish,matches);
78 vector<Category*> ::iterator aaa;
79 for(aaa=sub_categories.begin();aaa!=sub_categories.end();aaa++)
80 {
81 (*aaa)->findOfferingsRecursive(start,finish,matches);
82 }
83 }
84 istream &operator>>(istream &stream, Category &b)
85 {
86 int a;
87 string bb;
88 stream>>a;
89 stream>>bb;
90 b.setNumber(a);
91 b.setName(bb);
92 return stream;
93 }
94 bool Category::operator==(const Category& rhs)
95 {
96 if(this->getNumber()==rhs.getNumber())
97 {
98 return true;
99 }
100 return false;
101 }
 Client.h
1 #ifndef CLIENT_H
2 #define CLIENT_H
3
4 #include <string>
5 #include <vector>
6 #include "Date.h"
7
8 using namespace std;
9
10 class Client;
11
12 istream &operator>>(istream &stream, Client &c);
13
14 class Client {
15
16 private:
17
18 string fname;
19 string lname;
20 string email;
21 string passwd;
22 vector<int> offerings;
23 vector<int> bids;
24
25 public:
26
27 Client(void);
28 Client(Client const &c);
29 Client (string &fname, string &lname, string &email, string &passwd);
30
31 virtual void setFname(const string&);
32 virtual void setLname(const string&);
33 virtual void setEmail(const string&);
34 virtual void setPasswd(const string&);
35
36 virtual string getFname () const;
37 virtual string getLname () const;
38 virtual string getEmail () const;
39 virtual string getPasswd () const;
40
41 virtual vector<int>::iterator beginOfferings();
42 virtual vector<int>::iterator endOfferings();
43 virtual vector<int>::iterator beginBids();
44 virtual vector<int>::iterator endBids();
45
46 virtual void addBid (int item);
47 virtual void addOffering (int item);
48 virtual bool verifyPasswd(string passwd);
49
50 };
51
52 #endif
 Client.cpp
1 #include "Client.h"
2 Client::Client()
3 {
4 string fname;
5 string lname;
6 string email;
7 string passwd;
8 }
9 Client::Client(string &fname, string &lname, string &email, string &passwd)
10 {
11 this->fname=fname;
12 this->lname=lname;
13 this->email=email;
14 this->passwd=passwd;
15 }
16 Client::Client(Client const &c)
17 {
18 this->fname=c.getFname();
19 this->lname=c.getLname();
20 this->email=c.getEmail();
21 this->passwd=c.getPasswd();
22 }
23 void Client::setFname(const string &c)
24 {
25 this->fname=c;
26 }
27 void Client::setLname(const string &d)
28 {
29 this->lname=d;
30 }
31 void Client::setEmail(const string &e)
32 {
33 this->email=e;
34 }
35 void Client::setPasswd(const string &f)
36 {
37 this->passwd=f;
38 }
39 string Client::getFname () const
40 {
41 return this->fname;
42 }
43 string Client::getLname () const
44 {
45 return this->lname;
46 }
47 string Client::getEmail () const
48 {
49 return this->email;
50 }
51 string Client::getPasswd () const
52 {
53 return this->passwd;
54 }
55 bool Client::verifyPasswd(string passwd)
56 {
57 if(this->passwd==passwd)
58 {
59 return true;
60 }
61 else
62 {
63 return false;
64 }
65 }
66 istream &operator>>(istream &stream, Client &c)
67 {
68 string fname;
69 string lname;
70 string email;
71 string passwd;
72 stream>>fname;
73 stream>>lname;
74 stream>>email;
75 stream>>passwd;
76 c.setFname(fname);
77 c.setLname(lname);
78 c.setEmail(email);
79 c.setPasswd(passwd);
80 return stream;
81
82 }
83 vector<int>::iterator Client::beginOfferings()
84 {
85 return this->offerings.begin();
86 }
87 vector<int>::iterator Client::endOfferings()
88 {
89 return this->offerings.end();
90 }
91 vector<int>::iterator Client::beginBids()
92 {
93 return this->bids.begin();
94 }
95 vector<int>::iterator Client::endBids()
96 {
97 return this->bids.end();
98 }
99 void Client::addBid(int item)
100 {
101 this->bids.push_back(item);
102 }
103 void Client::addOffering(int item)
104 {
105 this->offerings.push_back(item);
106 }
 Date.h
1 #ifndef DATE_H
2 #define DATE_H
3
4 #include <iostream>
5
6 using namespace std;
7
8 class Date;
9
10 ostream &operator<<(ostream&, const Date&);
11 istream &operator>>(istream&, Date&);
12
13 class Date {
14
15 private:
16 int month;
17 int day;
18 int year;
19 int hour;
20 int minute;
21 int second;
22
23 public:
24
25 Date(void);
26 Date (int month, int day, int year, int hour, int minute, int second);
27
28 virtual void setMonth(int&);
29 virtual void setDay(int&);
30 virtual void setYear(int&);
31 virtual void setHour(int&);
32 virtual void setMinute(int&);
33 virtual void setSecond(int&);
34
35 virtual int getMonth(void) const;
36 virtual int getDay(void) const;
37 virtual int getYear(void) const;
38 virtual int getHour(void) const;
39 virtual int getMinute(void) const;
40 virtual int getSecond(void) const;
41
42 virtual bool operator== (const Date &rhs);
43 virtual bool operator< (const Date &left);
44
45 };
46
47 #endif
 Date.cpp
1 #include <iostream>
2 #include <string>
3 #include <cstdlib>
4 #include <sstream>
5 #include "Date.h"
6
7 Date::Date()
8 {
9 this->month=0;
10 this->day=0;
11 this->year=0;
12 this->hour=0;
13 this->minute=0;
14 this->second=0;
15 }
16 Date::Date(int month, int day, int year, int hour, int minute, int second)
17 {
18 this->month=month;
19 this->day=day;
20 this->year=year;
21 this->hour=hour;
22 this->minute=minute;
23 this->second=second;
24 }
25
26 void Date::setDay(int &day)
27 {
28 this->day=day;
29 }
30 void Date::setHour(int &hour)
31 {
32 this->hour=hour;
33 }
34 void Date::setMinute(int &minute)
35 {
36 this->minute=minute;
37 }
38 void Date::setMonth(int &month)
39 {
40 this->month=month;
41 }
42 void Date::setSecond(int &second)
43 {
44 this->second=second;
45 }
46 void Date::setYear(int &year)
47 {
48 this->year=year;
49 }
50 int Date::getDay(void) const
51 {
52 return this->day;
53 }
54 int Date::getHour(void)const
55 {
56 return this->hour;
57 }
58 int Date::getMinute(void)const
59 {
60 return this->minute;
61 }
62 int Date::getMonth(void)const
63 {
64 return this->month;
65 }
66 int Date::getSecond(void)const
67 {
68 return this->second;
69 }
70 int Date::getYear(void)const
71 {
72 return this->year;
73 }
74 bool Date::operator ==(const Date &rhs)
75 {
76 if(this->day==rhs.getDay()&&this->hour==rhs.getHour()&&this->minute==rhs.getMinute()&&this->month==rhs.getMonth()&&this->year==rhs.getYear())
77 {
78 return true;
79 }
80 else
81 {
82 return false;
83 }
84 }
85 bool Date::operator< (const Date &rhs)
86 {
87 if(this->year!=rhs.getYear())
88 {
89 if(this->year<rhs.getYear())
90 return true;
91 else
92 return false;
93 }
94 else if(this->month!=rhs.getMonth())
95 {
96 if(this->month<rhs.getMonth())
97 return true;
98 else
99 return false;
100 }
101 else if(this->day!=rhs.getDay())
102 {
103 if(this->day<rhs.getDay())
104 return true;
105 else
106 return false;
107 }
108 else if(this->hour!=rhs.getHour())
109 {
110 if(this->hour<rhs.getHour())
111 return true;
112 else
113 return false;
114 }
115 else if(this->minute!=rhs.getMinute())
116 {
117 if(this->minute<rhs.getMinute())
118 return true;
119 else
120 return false;
121 }
122 else if(this->second!=rhs.getSecond())
123 {
124 if(this->second<rhs.getSecond())
125 return true;
126 else
127 return false;
128 }
129 else
130 {
131 return false;
132 }
133
134 }
135 ostream &operator<<(ostream &out, const Date &c)
136 {
137 out<<c.getMonth()<<"/"<<c.getDay()<<"/"<<c.getYear()<<" "<<c.getHour()<<":"<<c.getMinute()<<":"<<c.getSecond();
138 return out;
139 }
140 istream &operator>>(istream& stream, Date &c)
141 {
142 int month;
143 int day;
144 int year;
145 int hour;
146 int minute;
147 int second;
148 char a;
149 char b;
150 char cx;
151 char d;
152 char e;
153
154 stream>>month;
155 stream>>a;
156 stream>>day;
157 stream>>b;
158 stream>>year;
159
160 stream>>hour;
161 stream>>d;
162 stream>>minute;
163 stream>>e;
164 stream>>second;
165 c.setDay(day);
166 c.setHour(hour);
167 c.setMinute(minute);
168 c.setMonth(month);
169 c.setSecond(second);
170 c.setYear(year);
171 return stream;
172 }
 Group.h
1 #ifndef GROUP_H
2 #define GROUP_H
3
4 #include <iostream>
5 #include <vector>
6 #include <iterator>
7 #include <algorithm>
8 #include <functional>
9
10 #include "Client.h"
11
12 using namespace std;
13
14 class Group;
15
16 class Group {
17
18 protected:
19 typedef vector<Client*> Container;
20
21 public:
22 typedef Container::iterator iterator;
23
24 protected:
25 Container objects;
26
27 public:
28 Client *operator[](const string& email);
29
30 virtual void add(Client* ptr);
31
32 virtual iterator begin();
33 virtual iterator end();
34
35 };
36
37 #endif
 Group.cpp
1 #include "Group.h"
2 void Group::add(Client* ptr)
3 {
4 objects.push_back(ptr);
5 }
6 vector<Client*> ::iterator Group::begin()
7 {
8 return objects.begin();
9 }
10 vector<Client*> ::iterator Group::end()
11 {
12 return objects.end();
13 }
14 Client * Group::operator[](const string& email)
15 {
16 for(vector<Client*> ::iterator aaa=objects.begin();aaa!=objects.end();aaa++)
17 {
18 if((*aaa)->getEmail()==email)
19 {
20 return *aaa;
21 }
22 }
23 return NULL;
24 }
 Listing.h
1 #ifndef LISTING_H
2 #define LISTING_H
3
4 #include <iostream>
5 #include <vector>
6 #include <iterator>
7 #include <algorithm>
8 #include <functional>
9
10 #include "Advertisement.h"
11
12 using namespace std;
13
14 class Listing;
15
16 class Listing {
17
18 protected:
19 typedef vector<Advertisement*> Container;
20
21 public:
22 typedef Container::iterator iterator;
23
24 protected:
25 Container objects;
26
27 public:
28 virtual Advertisement* operator[](const int& number);
29
30 virtual void add(Advertisement* ptr);
31
32 virtual iterator begin();
33 virtual iterator end();
34
35 // return a sorted copy of this Listing
36 virtual Listing sort(string field);
37
38 // return a filtered by keyword copy of this Listing
39 virtual Listing filter(string keyword);
40 };
41
42 #endif
 Listing.cpp
1 #include "Listing.h"
2
3
4 void Listing::add(Advertisement* ptr)
5 {
6 objects.push_back(ptr);
7
8 }
9 vector<Advertisement*>::iterator Listing::begin()
10 {
11
12 return objects.begin();
13 }
14 vector<Advertisement*>::iterator Listing::end()
15 {
16 return objects.end();
17 }
18 Advertisement* Listing::operator[](const int& number)
19 {
20 for(vector<Advertisement*> ::iterator aa=objects.begin();aa!=objects.end();aa++)
21 {
22 if((*aa)->getNumber()==number)
23 {
24 return *aa;
25 }
26 }
27 return NULL;
28 }
29 bool cmp4(Advertisement *m1,Advertisement *m2)
30 {
31 if(m1->getQuantity()<m2->getQuantity())
32 {
33 return true;
34 }
35 return false;
36 }
37 bool cmp1(Advertisement *m1,Advertisement *m2)
38 {
39 int a=m1->getEmail().compare(m2->getEmail());
40 if(a<0)
41 {
42 return true;
43 }
44 else
45 {
46 return false;
47 }
48 }
49 bool cmp2(Advertisement *m1,Advertisement *m2)
50 {
51 return m1->getStart()<m2->getStart();
52 }
53 bool cmp3(Advertisement *m1,Advertisement *m2)
54 {
55 return m1->getClose()<m2->getClose();
56 }
57 Listing Listing::sort(string field)
58 {
59 Listing cp;
60 cp.objects=this->objects;
61 if(field=="email")
62 {
63 std::sort(cp.objects.begin(),cp.objects.end(),cmp1);
64 return cp;
65 }
66 else if(field=="start")
67 {
68 std::sort(cp.objects.begin(),cp.objects.end(),cmp2);
69 return cp;
70 }
71 else if(field=="end")
72 {
73 std::sort(cp.objects.begin(),cp.objects.end(),cmp3);
74 return cp;
75 }
76 else
77 {
78 std::sort(cp.objects.begin(),cp.objects.end(),cmp4);
79 return cp;
80 }
81 }
82 Listing l;
83 struct F
84 {
85 string key;
86
87 F(string keyword):key(keyword){}
88 void operator() (Advertisement* a)
89 {
90 if(a->getTitle().find(key)!=string::npos||a->getBody().find(key)!=string::npos)
91 {
92 l.add(a);
93 }
94 }
95
96 };
97 Listing Listing::filter(string keyword)
98 {
99
100
101 if(keyword=="")
102 {
103 return l;
104 }
105 else
106 {
107 l.objects.clear();
108 std::for_each(this->begin(),this->end(),F(keyword));
109 return l;
110 }
111
112 }
 main.h
1 #ifndef MAIN_H
2 #define MAIN_H
3
4 #include "Listing.h"
5 #include "Categories.h"
6 #include "Group.h"
7
8 #define BACKLOG 11
9 #define REQ_MAX 8192
10
11 extern Categories categories;
12 extern Listing advertisements;
13 extern Group users;
14
15 extern string active_user;
16
17 extern int category_counter;
18 extern int advertisement_counter;
19
20 extern bool create_verified;
21 extern bool login_failed;
22
23 #endif
 main.cpp
1 #include <winsock2.h>
2 #include <ws2tcpip.h>
3 #include <signal.h>
4 #include <cstdio>
5
6 #include <string>
7 #include <fcntl.h>
8 #include <errno.h>
9 #include <iostream>
10 #include <sstream>
11
12 #include "Listing.h"
13 #include "Group.h"
14 #include "Categories.h"
15 #include "processrequest.h"
16 #include "main.h"
17
18 using namespace std;
19
20 Categories categories;
21 Listing advertisements;
22 Group users;
23
24 int category_counter = 0;
25 int advertisement_counter = 0;
26
27 string active_user = "";
28 bool create_verified = true;
29 bool login_failed = false;
30
31
32 /*
33 * Not this is explicitly not concurrent -- the auction data structures
34 * are not necessarily concurrency safe
35 */
36
37 int main (int argc, char *argv[]) {
38
39
40
41 /*
42 * argv[1] should be the port number
43 */
44 if (2 != argc) {
45 cout << "Usage: " << argv[0] << " [port]" << endl << endl;
46 return -1;
47 }
48
49 int port = atoi(argv[1]);
50
51
52 WORD wVersionRequested;
53 WSADATA wsaData;
54 int err;
55
56 wVersionRequested = MAKEWORD( 2, 2 );
57
58 err = WSAStartup( wVersionRequested, &wsaData );
59 if ( err != 0 ) {
60 /* Tell the user that we could not find a usable */
61 /* WinSock DLL. */
62 return 0;
63 }
64
65
66
67 /*
68 * Create and configure the socket
69 */
70 int connfd = -1;
71 int listenfd = -1;
72
73 struct sockaddr_in cliaddr;
74 struct sockaddr_in servaddr;
75 int clilen = sizeof (cliaddr);
76
77 listenfd = socket (AF_INET, SOCK_STREAM, 0);
78
79 memset(&servaddr, 0, sizeof(servaddr));
80 servaddr.sin_family = AF_INET;
81 servaddr.sin_addr.s_addr = htonl (INADDR_ANY);
82 servaddr.sin_port = htons(port);
83
84
85 /*
86 * Bind to the socket
87 */
88 ::bind (listenfd, (struct sockaddr *)&servaddr, sizeof(servaddr));
89
90
91 /*
92 * Configure the listen queue
93 */
94 listen (listenfd, BACKLOG);
95
96 /*
97 * Main work loop:
98 * Listen for connection, accept it, process request, print html page
99 */
100
101 Category top_level(Categories::NO_PARENT, "Top Level");
102 top_level.setNumber(category_counter);
103 category_counter++;
104
105 categories.add(new Category(top_level));
106
107
108 while (true) {
109
110 // Wait for the knock at the door
111 if (0 > (connfd = accept (listenfd,
112 (struct sockaddr *) &cliaddr, &clilen)) ) {
113
114 if (errno == EINTR)
115 continue;
116 else {
117 cerr << "unknown error: " << errno << " " << connfd << endl;
118 exit(-1); // Who knows? Bad foo. Maybe continue for roubustness?
119
120 }
121
122 }
123
124 // Process the request
125 char req_buffer[REQ_MAX];
126 int count;
127
128
129
130 for (count=0; count<REQ_MAX; count++) {
131 int retval = recv (connfd, req_buffer+count, 1, 0);
132
133 if (4 == req_buffer[count]) { // 4 is EOT, a.ka. CTRL-D
134 req_buffer[count] = '\0';
135 break;
136 }
137 }
138
139
140 // Move request to stream for C++ style processing
141 ostringstream oss;
142 oss.str("");
143 oss << req_buffer;
144 memset (req_buffer, 0, REQ_MAX);
145
146 cerr << oss.str() << endl;
147
148 istringstream iss (oss.str());
149
150 processrequest (iss, connfd, port);
151
152 // Done with this request
153 closesocket (connfd);
154 connfd = -1;
155 }
156
157 }
 processrequest.h
1 #ifndef PROCESS_REQUEST_H
2 #define PROCESS_REQUEST_H
3
4 #include <sstream>
5 #include "buildpage.h"
6 #include "buildbidpage.h"
7
8 using namespace std;
9
10 void processrequest(istringstream &iss, int connfd, int port);
11
12 #endif
 processrequest.cpp
1 #pragma warning(disable:4786)
2
3 #include <sstream>
4 #include <set>
5 #include <string>
6 #include <winsock2.h>
7 #include <ws2tcpip.h>
8 #include <fcntl.h>
9 #include <errno.h>
10
11 #include "processrequest.h"
12 #include "main.h"
13 #include "Advertisement.h"
14 #include "Listing.h"
15 #include "Client.h"
16 #include "Categories.h"
17 //#include "CopyByKeyword.h"
18 //#include "SortBy.h"
19
20 using namespace std;
21
22 void displayListing(int connfd, int port,
23 Listing::iterator begin, Listing::iterator end) {
24
25 ostringstream oss ("");
26 buildpage (oss, port, begin, end);
27 send (connfd, oss.str().c_str(), strlen (oss.str().c_str()), 0);
28 }
29
30
31
32
33 void processrequest(istringstream &iss, int connfd, int port) {
34
35 char request[80];
36 memset (request, 0, 80);
37 iss.getline (request, 80);
38 string req(request);
39
40 // instead of the above, we could have
41 // just as easily done
42 // getline(iss, req)
43 // but there is a bug in MSVC++ getline, so
44 // using the C-style string here is more portable
45
46 if (req == "LOGIN") {
47
48 string email;
49 string passwd;
50
51 iss >> email;
52 iss >> passwd;
53
54 /*
55 * Find the client's record in the set
56 */
57 Client* search_results = users[email];
58
59 if (search_results != NULL) {
60
61 if (search_results->verifyPasswd(passwd)) {
62 active_user = email;
63 login_failed = false;
64 }
65 else {
66 login_failed = true;
67 }
68 }
69 else {
70 login_failed = true;
71 }
72
73 displayListing(connfd, port, advertisements.begin(), advertisements.end());
74 }
75
76 else if (req == "LOGOUT") {
77 active_user = "";
78 displayListing(connfd, port, advertisements.begin(), advertisements.end());
79 }
80
81 else if (req == "BID_REQUEST") {
82
83 int number;
84 iss.getline(request, 80);
85 number = atoi(request);
86
87 ostringstream oss ("");
88 buildbidpage (oss, port, number);
89 send (connfd, oss.str().c_str(), strlen (oss.str().c_str()), 0);
90
91 }
92
93 else if (req == "BID_SUBMIT") {
94
95 // Add the bid
96 int number;
97 iss.getline(request, 80);
98 number = atoi(request);
99
100 Bid newBid;
101 iss >> newBid;
102 Advertisement* ad = advertisements[number];
103
104 if (newBid.getQuantity() < 1) {
105 newBid.setQuantity(1);
106 } else if (newBid.getQuantity() > ad->getQuantity()) {
107 newBid.setQuantity(ad->getQuantity());
108 }
109
110 ad->getBids().push(newBid);
111
112 // Take care of accounting in client record
113 Client* client = users[active_user];
114 client->addBid(number);
115
116 displayListing(connfd, port, advertisements.begin(), advertisements.end());
117 }
118
119 else if (req == "CREATE") {
120
121 string verify;
122 Client client;
123 iss >> client;
124 iss >> verify;
125
126 /*
127 * Check for existing user
128 */
129 Client* search_results = users[client.getEmail()];
130
131 if ( (client.verifyPasswd (verify)) && (search_results == NULL) ){
132
133 active_user = client.getEmail();
134 Client* new_client = new Client(client);
135
136 users.add (new_client);
137 create_verified = true;
138 }
139 else {
140 create_verified = false;
141 }
142
143 displayListing(connfd, port, advertisements.begin(), advertisements.end());
144 }
145
146 else if (req == "ADD") {
147
148 int category;
149 iss.getline(request, 80);
150 category = atoi(request);
151
152 Advertisement ad;
153 iss >> ad;
154 ad.setNumber(advertisement_counter);
155 advertisement_counter++;
156
157 advertisements.add(new Advertisement(ad));
158
159 Category* cat = categories[category];
160 cat->addItem(ad.getNumber());
161
162 Client* client = users[ad.getEmail()];
163 client->addOffering(ad.getNumber());
164
165 displayListing(connfd, port, advertisements.begin(), advertisements.end());
166 }
167
168 else if (req == "CATEGORY_ADD") {
169
170 Category cat;
171 iss >> cat;
172
173 Category* p = categories[cat.getParent()];
174 Category* a=p;
175
176 cat.setName(p->getName() + " / " + cat.getName());
177
178 cat.setNumber(category_counter);
179 category_counter++;
180
181 Category* c = new Category(cat);
182 categories.add(c);
183 p->addSubCategory(c);
184
185
186
187
188
189
190 displayListing(connfd, port, advertisements.begin(), advertisements.end());
191 }
192
193 else if (req == "TOP_ONLY") {
194
195 int category;
196 iss.getline(request, 80);
197 category = atoi(request);
198
199 Listing filteredByCategory;
200 Category* c = categories[category];
201
202 c->findOfferings (advertisements.begin(), advertisements.end(),
203 filteredByCategory );
204 displayListing(connfd, port, filteredByCategory.begin(), filteredByCategory.end());
205
206 }
207 else if (req == "RECURSIVE") {
208
209 int category;
210 iss.getline(request, 80);
211 category = atoi(request);
212
213
214 Listing filteredByCategory;
215 Category* c = categories[category];
216
217 c->findOfferingsRecursive (advertisements.begin(),
218 advertisements.end(), filteredByCategory );
219 displayListing(connfd, port, filteredByCategory.begin(), filteredByCategory.end());
220
221 }
222
223
224 else if (req == "SORT") {
225
226 string field;
227 iss >> field;
228
229 Listing sorted = advertisements.sort(field);
230 displayListing(connfd, port, sorted.begin(), sorted.end());
231 }
232 else if (req == "FIND") {
233
234 string keyword;
235 iss >> keyword;
236
237 Listing filtered = advertisements.filter(keyword);
238
239 displayListing(connfd, port, filtered.begin(), filtered.end());
240 }
241
242
243 else if (req == "" || req == "LIST") {
244 displayListing(connfd, port, advertisements.begin(), advertisements.end());
245 }
246
247 else {
248 // unknown command! Let's just list to play it safe...
249 displayListing(connfd, port, advertisements.begin(), advertisements.end());
250 }
251
252 }
|
|
|