Spaces:
Running
Running
Update main.py
Browse files
main.py
CHANGED
@@ -4,217 +4,16 @@ import random
|
|
4 |
|
5 |
from flask import Flask, request, jsonify, redirect, url_for
|
6 |
from flask_cors import CORS
|
7 |
-
from flask_jwt_extended import JWTManager, create_access_token
|
8 |
-
from flask_jwt_extended import jwt_required, get_jwt_identity
|
9 |
-
from flask_dance.contrib.google import make_google_blueprint, google
|
10 |
-
from werkzeug.security import generate_password_hash, check_password_hash
|
11 |
-
import sqlite3
|
12 |
|
13 |
client = InferenceClient("mistralai/Mistral-7B-Instruct-v0.1")
|
14 |
|
15 |
app = Flask(__name__)
|
16 |
CORS(app)
|
17 |
-
|
18 |
-
file_path = "mentor.txt"
|
19 |
-
with open(file_path, "r") as file:
|
20 |
-
mentors_data = file.read()
|
21 |
-
|
22 |
-
file_path = "temp_mentor.txt"
|
23 |
-
with open(file_path, "r") as file:
|
24 |
-
temp_mentors_data = file.read()
|
25 |
|
26 |
@app.route('/')
|
27 |
def home():
|
28 |
return jsonify({"message": "Welcome to the Recommendation API!"})
|
29 |
|
30 |
-
app.config['JWT_SECRET_KEY'] = "123456"
|
31 |
-
jwt = JWTManager(app)
|
32 |
-
|
33 |
-
# Setup Google OAuth
|
34 |
-
app.config["GOOGLE_OAUTH_CLIENT_ID"] = "991031782679-f0fv60jqr9snq5u9cl7j5eimhi1b3ukp.apps.googleusercontent.com"
|
35 |
-
app.config["GOOGLE_OAUTH_CLIENT_SECRET"] = "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"
|
36 |
-
google_bp = make_google_blueprint(scope=["profile", "email"])
|
37 |
-
app.register_blueprint(google_bp, url_prefix="/login")
|
38 |
-
|
39 |
-
# Create SQLite database
|
40 |
-
conn = sqlite3.connect('users.db', check_same_thread=False)
|
41 |
-
c = conn.cursor()
|
42 |
-
c.execute('''CREATE TABLE IF NOT EXISTS users
|
43 |
-
(id INTEGER PRIMARY KEY AUTOINCREMENT, username TEXT UNIQUE, password TEXT)''')
|
44 |
-
|
45 |
-
c.execute('''CREATE TABLE IF NOT EXISTS user_details
|
46 |
-
(id INTEGER PRIMARY KEY AUTOINCREMENT,
|
47 |
-
user_id INTEGER UNIQUE,
|
48 |
-
first_name TEXT,
|
49 |
-
last_name TEXT,
|
50 |
-
school_name TEXT,
|
51 |
-
bachelors_degree TEXT,
|
52 |
-
masters_degree TEXT,
|
53 |
-
certification TEXT,
|
54 |
-
activity TEXT,
|
55 |
-
country TEXT,
|
56 |
-
data_filled BOOLEAN DEFAULT False,
|
57 |
-
FOREIGN KEY(user_id) REFERENCES users(id))''')
|
58 |
-
|
59 |
-
|
60 |
-
c.execute('''CREATE TABLE IF NOT EXISTS user_mentor
|
61 |
-
(id INTEGER PRIMARY KEY AUTOINCREMENT, user_id INTEGER, mentor_name TEXT,
|
62 |
-
FOREIGN KEY(user_id) REFERENCES users(id))''')
|
63 |
-
conn.commit()
|
64 |
-
|
65 |
-
@app.route('/register', methods=['POST'])
|
66 |
-
def register():
|
67 |
-
data = request.get_json()
|
68 |
-
username = data.get('username')
|
69 |
-
password = data.get('password')
|
70 |
-
google_token = data.get('google_token')
|
71 |
-
|
72 |
-
print("Type of username:", type(username))
|
73 |
-
|
74 |
-
|
75 |
-
if google_token:
|
76 |
-
# User signing up with Google
|
77 |
-
resp = google.get("/oauth2/v2/userinfo")
|
78 |
-
if not resp.ok:
|
79 |
-
return jsonify({"message": "Failed to fetch Google user info"}), 400
|
80 |
-
google_user_info = resp.json()
|
81 |
-
google_id = google_user_info["id"]
|
82 |
-
username = google_user_info["email"]
|
83 |
-
password = None # No password for Google signup
|
84 |
-
|
85 |
-
# Check if Google user already exists in the database
|
86 |
-
existing_user = c.execute("SELECT * FROM users WHERE google_id=?", (google_id,)).fetchone()
|
87 |
-
if existing_user:
|
88 |
-
access_token = create_access_token(identity=username, expires_delta=False)
|
89 |
-
return jsonify({"access_token": access_token}), 200
|
90 |
-
|
91 |
-
# User signing up with username and password
|
92 |
-
if not username or not password:
|
93 |
-
return jsonify({"message": "Missing username or password"}), 400
|
94 |
-
|
95 |
-
print("Type of username:", type(username)) # Debug print
|
96 |
-
|
97 |
-
hashed_password = generate_password_hash(password)
|
98 |
-
try:
|
99 |
-
c.execute("INSERT INTO users (username, password) VALUES (?, ?)", (username, hashed_password))
|
100 |
-
conn.commit()
|
101 |
-
access_token = create_access_token(identity=username, expires_delta=False)
|
102 |
-
return jsonify({"access_token": access_token}), 201
|
103 |
-
except sqlite3.IntegrityError:
|
104 |
-
return jsonify({"message": "Username already exists"}), 400
|
105 |
-
|
106 |
-
# Endpoint for user login and Google login
|
107 |
-
@app.route('/login', methods=['POST'])
|
108 |
-
def login():
|
109 |
-
data = request.get_json()
|
110 |
-
username = data.get('username')
|
111 |
-
password = data.get('password')
|
112 |
-
google_token = data.get('google_token')
|
113 |
-
|
114 |
-
if google_token:
|
115 |
-
# User logging in with Google
|
116 |
-
resp = google.get("/oauth2/v2/userinfo")
|
117 |
-
if not resp.ok:
|
118 |
-
return jsonify({"message": "Failed to fetch Google user info"}), 400
|
119 |
-
google_user_info = resp.json()
|
120 |
-
google_id = google_user_info["id"]
|
121 |
-
|
122 |
-
# Check if Google user exists in the database
|
123 |
-
user = c.execute("SELECT * FROM users WHERE google_id=?", (google_id,)).fetchone()
|
124 |
-
if user:
|
125 |
-
# Retrieve data_filled from user_details table
|
126 |
-
user_details = c.execute("SELECT data_filled FROM user_details WHERE user_id=?", (user[0],)).fetchone()
|
127 |
-
if user_details:
|
128 |
-
data_filled = user_details[0]
|
129 |
-
else:
|
130 |
-
data_filled = False # Default value if data not found
|
131 |
-
access_token = create_access_token(identity=user[1], expires_delta=False)
|
132 |
-
return jsonify({"access_token": access_token, "data_filled": data_filled}), 200
|
133 |
-
else:
|
134 |
-
return jsonify({"message": "User not found"}), 404
|
135 |
-
|
136 |
-
# User logging in with username and password
|
137 |
-
if not username or not password:
|
138 |
-
return jsonify({"message": "Missing username or password"}), 400
|
139 |
-
|
140 |
-
user = c.execute("SELECT * FROM users WHERE username=?", (username,)).fetchone()
|
141 |
-
print(user)
|
142 |
-
if user and check_password_hash(user[2], password):
|
143 |
-
# Retrieve data_filled from user_details table
|
144 |
-
user_details = c.execute("SELECT data_filled FROM user_details WHERE user_id=?", (user[0],)).fetchone()
|
145 |
-
if user_details:
|
146 |
-
data_filled = user_details[0]
|
147 |
-
else:
|
148 |
-
data_filled = False # Default value if data not found
|
149 |
-
access_token = create_access_token(identity=username, expires_delta=False)
|
150 |
-
return jsonify({"access_token": access_token, "data_filled": data_filled}), 200
|
151 |
-
else:
|
152 |
-
return jsonify({"message": "Invalid username or password"}), 401
|
153 |
-
|
154 |
-
|
155 |
-
|
156 |
-
@app.route('/user_details', methods=['POST'])
|
157 |
-
@jwt_required()
|
158 |
-
def add_user_details():
|
159 |
-
current_user = get_jwt_identity()
|
160 |
-
data = request.get_json()
|
161 |
-
first_name = data.get('first_name')
|
162 |
-
last_name = data.get('last_name')
|
163 |
-
school_name = data.get('school_name')
|
164 |
-
bachelors_degree = data.get('bachelors_degree')
|
165 |
-
masters_degree = data.get('masters_degree')
|
166 |
-
certification = data.get('certification')
|
167 |
-
activity = data.get('activity')
|
168 |
-
country = data.get('country')
|
169 |
-
|
170 |
-
if not all([first_name, last_name, school_name, bachelors_degree, masters_degree, certification, activity, country]):
|
171 |
-
return jsonify({"message": "Missing required fields"}), 400
|
172 |
-
|
173 |
-
user = c.execute("SELECT * FROM users WHERE username=?", (current_user,)).fetchone()
|
174 |
-
if not user:
|
175 |
-
return jsonify({"message": "User not found"}), 404
|
176 |
-
|
177 |
-
user_id = user[0]
|
178 |
-
try:
|
179 |
-
c.execute("INSERT INTO user_details (user_id, first_name, last_name, school_name, bachelors_degree, "
|
180 |
-
"masters_degree, certification, activity, country, data_filled) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
|
181 |
-
(user_id, first_name, last_name, school_name, bachelors_degree, masters_degree, certification,
|
182 |
-
activity, country, "True"))
|
183 |
-
conn.commit()
|
184 |
-
return jsonify({"message": "User details added successfully"}), 201
|
185 |
-
except sqlite3.IntegrityError:
|
186 |
-
return jsonify({"message": "User details already exist"}), 400
|
187 |
-
|
188 |
-
|
189 |
-
@app.route('/user_details', methods=['GET'])
|
190 |
-
@jwt_required()
|
191 |
-
def get_user_details():
|
192 |
-
current_user = get_jwt_identity()
|
193 |
-
|
194 |
-
user = c.execute("SELECT * FROM users WHERE username=?", (current_user,)).fetchone()
|
195 |
-
if not user:
|
196 |
-
return jsonify({"message": "User not found"}), 404
|
197 |
-
|
198 |
-
user_id = user[0]
|
199 |
-
user_details = c.execute("SELECT * FROM user_details WHERE user_id=?", (user_id,)).fetchone()
|
200 |
-
if not user_details:
|
201 |
-
return jsonify({"message": "User details not found"}), 404
|
202 |
-
|
203 |
-
user_details_dict = {
|
204 |
-
"first_name": user_details[2],
|
205 |
-
"last_name": user_details[3],
|
206 |
-
"school_name": user_details[4],
|
207 |
-
"bachelors_degree": user_details[5],
|
208 |
-
"masters_degree": user_details[6],
|
209 |
-
"certification": user_details[7],
|
210 |
-
"activity": user_details[8],
|
211 |
-
"country": user_details[9],
|
212 |
-
"data_filled": user_details[10]
|
213 |
-
}
|
214 |
-
|
215 |
-
return jsonify(user_details_dict), 200
|
216 |
-
|
217 |
-
|
218 |
|
219 |
def format_prompt(message):
|
220 |
# Generate a random user prompt and bot response pair
|
@@ -223,63 +22,9 @@ def format_prompt(message):
|
|
223 |
|
224 |
return f"<s>[INST] {user_prompt} [/INST] {bot_response}</s> [INST] {message} [/INST]"
|
225 |
|
226 |
-
@app.route('/add_mentor', methods=['POST'])
|
227 |
-
def add_mentor():
|
228 |
-
data = request.get_json()
|
229 |
-
mentor_name = data.get('name')
|
230 |
-
skills = data.get('skills')
|
231 |
-
qualification = data.get('qualification')
|
232 |
-
experience = data.get('experience')
|
233 |
-
|
234 |
-
if not all([mentor_name, skills, qualification, experience]):
|
235 |
-
return jsonify({"message": "Missing mentor details"}), 400
|
236 |
-
|
237 |
-
mentor_details = f"\n{mentor_name}\nSkills: {skills}\nQualification: {qualification}\nExperience: {experience}\n"
|
238 |
-
|
239 |
-
try:
|
240 |
-
with open("temp_mentor.txt", "a") as file:
|
241 |
-
file.write(mentor_details)
|
242 |
-
return jsonify({"message": "Mentor will be added after verification"}), 201
|
243 |
-
except Exception as e:
|
244 |
-
return jsonify({"message": f"Failed to add mentor: {str(e)}"}), 500
|
245 |
-
|
246 |
-
@app.route('/verify_mentor', methods=['POST'])
|
247 |
-
def verify_mentor():
|
248 |
-
try:
|
249 |
-
with open("temp_mentor.txt", "r") as file:
|
250 |
-
mentors = file.readlines()
|
251 |
-
|
252 |
-
if not mentors:
|
253 |
-
return jsonify({"message": "No mentors to verify"}), 404
|
254 |
-
|
255 |
-
return jsonify({"mentors": mentors}), 200
|
256 |
-
except Exception as e:
|
257 |
-
return jsonify({"message": f"Failed to retrieve mentors: {str(e)}"}), 500
|
258 |
-
|
259 |
-
@app.route('/add_verified_mentors', methods=['POST'])
|
260 |
-
def add_verified_mentors():
|
261 |
-
try:
|
262 |
-
data = request.get_json()
|
263 |
-
|
264 |
-
if 'mentors' not in data:
|
265 |
-
return jsonify({"message": "Mentors data not found in request"}), 400
|
266 |
-
|
267 |
-
mentors = data['mentors']
|
268 |
-
|
269 |
-
with open("mentor.txt", "a") as mentor_file:
|
270 |
-
for mentor_details in mentors:
|
271 |
-
mentor_file.write(mentor_details + '\n')
|
272 |
-
|
273 |
-
open("temp_mentor.txt", "w").close()
|
274 |
-
|
275 |
-
return jsonify({"message": "Mentors added successfully"}), 200
|
276 |
-
except Exception as e:
|
277 |
-
return jsonify({"message": f"Failed to add mentors: {str(e)}"}), 500
|
278 |
|
279 |
@app.route('/ai_mentor', methods=['POST'])
|
280 |
-
@jwt_required()
|
281 |
def ai_mentor():
|
282 |
-
current_user = get_jwt_identity()
|
283 |
data = request.get_json()
|
284 |
message = data.get('message')
|
285 |
|
@@ -317,9 +62,7 @@ def ai_mentor():
|
|
317 |
|
318 |
|
319 |
@app.route('/get_course', methods=['POST'])
|
320 |
-
@jwt_required()
|
321 |
def get_course():
|
322 |
-
current_user = get_jwt_identity()
|
323 |
temperature = 0.9
|
324 |
max_new_tokens = 256
|
325 |
top_p = 0.95
|
@@ -355,9 +98,7 @@ def get_course():
|
|
355 |
|
356 |
|
357 |
@app.route('/get_mentor', methods=['POST'])
|
358 |
-
@jwt_required()
|
359 |
def get_mentor():
|
360 |
-
current_user = get_jwt_identity()
|
361 |
temperature = 0.9
|
362 |
max_new_tokens = 256
|
363 |
top_p = 0.95
|
@@ -368,6 +109,7 @@ def get_mentor():
|
|
368 |
user_stream = content.get('stream')
|
369 |
#user_semester = content.get('semester')
|
370 |
courses = content.get('courses')
|
|
|
371 |
|
372 |
temperature = float(temperature)
|
373 |
if temperature < 1e-2:
|
@@ -382,9 +124,6 @@ def get_mentor():
|
|
382 |
do_sample=True,
|
383 |
seed=42,
|
384 |
)
|
385 |
-
file_path = "mentor.txt"
|
386 |
-
with open(file_path, "r") as file:
|
387 |
-
mentors_data = file.read()
|
388 |
|
389 |
prompt = f""" prompt:
|
390 |
You need to act like as recommendataion engine for mentor recommendation for student based on below details also the list of mentors with their experience is attached.
|
@@ -402,62 +141,6 @@ def get_mentor():
|
|
402 |
stream = client.text_generation(formatted_prompt, **generate_kwargs, stream=False, details=False, return_full_text=False)
|
403 |
return jsonify({"ans": stream})
|
404 |
|
405 |
-
@app.route('/select_mentor', methods=['POST'])
|
406 |
-
@jwt_required()
|
407 |
-
def select_mentor():
|
408 |
-
current_user = get_jwt_identity()
|
409 |
-
data = request.get_json()
|
410 |
-
mentor_name = data.get('mentor_name') # Assuming this is the name of the selected mentor
|
411 |
-
|
412 |
-
if not mentor_name:
|
413 |
-
return jsonify({"message": "Missing mentor name"}), 400
|
414 |
-
|
415 |
-
# Fetch user details
|
416 |
-
user = c.execute("SELECT * FROM users WHERE username=?", (current_user,)).fetchone()
|
417 |
-
if not user:
|
418 |
-
return jsonify({"message": "User not found"}), 404
|
419 |
-
|
420 |
-
user_id = user[0]
|
421 |
-
|
422 |
-
try:
|
423 |
-
# Store selected mentor information in a new table
|
424 |
-
c.execute("INSERT INTO user_mentor (user_id, mentor_name) VALUES (?, ?)", (user_id, mentor_name))
|
425 |
-
conn.commit()
|
426 |
-
return jsonify({"message": "Mentor selected successfully"}), 201
|
427 |
-
except sqlite3.IntegrityError:
|
428 |
-
return jsonify({"message": "Failed to select mentor"}), 500
|
429 |
-
|
430 |
-
@app.route('/get_all_mentors', methods=['POST'])
|
431 |
-
def get_all_mentors():
|
432 |
-
try:
|
433 |
-
with open("mentor.txt", "r") as file:
|
434 |
-
mentors = file.readlines()
|
435 |
-
|
436 |
-
if not mentors:
|
437 |
-
return jsonify({"message": "No mentors"}), 404
|
438 |
-
|
439 |
-
return jsonify({"mentors": mentors}), 200
|
440 |
-
except Exception as e:
|
441 |
-
return jsonify({"message": f"Failed to retrieve mentors: {str(e)}"}), 500
|
442 |
-
|
443 |
-
@app.route('/users', methods=['GET'])
|
444 |
-
def get_all_users():
|
445 |
-
try:
|
446 |
-
users = c.execute("SELECT * FROM users").fetchall()
|
447 |
-
users_list = [{"id": user[0], "username": user[1]} for user in users]
|
448 |
-
return jsonify({"users": users_list}), 200
|
449 |
-
except Exception as e:
|
450 |
-
return jsonify({"message": f"Failed to retrieve users: {str(e)}"}), 500
|
451 |
-
|
452 |
-
@app.route('/users', methods=['DELETE'])
|
453 |
-
def delete_all_users():
|
454 |
-
try:
|
455 |
-
c.execute("DELETE FROM users")
|
456 |
-
conn.commit()
|
457 |
-
return jsonify({"message": "All users deleted successfully"}), 200
|
458 |
-
except Exception as e:
|
459 |
-
return jsonify({"message": f"Failed to delete users: {str(e)}"}), 500
|
460 |
-
|
461 |
|
462 |
if __name__ == '__main__':
|
463 |
app.run(debug=True)
|
|
|
4 |
|
5 |
from flask import Flask, request, jsonify, redirect, url_for
|
6 |
from flask_cors import CORS
|
|
|
|
|
|
|
|
|
|
|
7 |
|
8 |
client = InferenceClient("mistralai/Mistral-7B-Instruct-v0.1")
|
9 |
|
10 |
app = Flask(__name__)
|
11 |
CORS(app)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
12 |
|
13 |
@app.route('/')
|
14 |
def home():
|
15 |
return jsonify({"message": "Welcome to the Recommendation API!"})
|
16 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
17 |
|
18 |
def format_prompt(message):
|
19 |
# Generate a random user prompt and bot response pair
|
|
|
22 |
|
23 |
return f"<s>[INST] {user_prompt} [/INST] {bot_response}</s> [INST] {message} [/INST]"
|
24 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
25 |
|
26 |
@app.route('/ai_mentor', methods=['POST'])
|
|
|
27 |
def ai_mentor():
|
|
|
28 |
data = request.get_json()
|
29 |
message = data.get('message')
|
30 |
|
|
|
62 |
|
63 |
|
64 |
@app.route('/get_course', methods=['POST'])
|
|
|
65 |
def get_course():
|
|
|
66 |
temperature = 0.9
|
67 |
max_new_tokens = 256
|
68 |
top_p = 0.95
|
|
|
98 |
|
99 |
|
100 |
@app.route('/get_mentor', methods=['POST'])
|
|
|
101 |
def get_mentor():
|
|
|
102 |
temperature = 0.9
|
103 |
max_new_tokens = 256
|
104 |
top_p = 0.95
|
|
|
109 |
user_stream = content.get('stream')
|
110 |
#user_semester = content.get('semester')
|
111 |
courses = content.get('courses')
|
112 |
+
mentors_data= content.get('mentors_data')
|
113 |
|
114 |
temperature = float(temperature)
|
115 |
if temperature < 1e-2:
|
|
|
124 |
do_sample=True,
|
125 |
seed=42,
|
126 |
)
|
|
|
|
|
|
|
127 |
|
128 |
prompt = f""" prompt:
|
129 |
You need to act like as recommendataion engine for mentor recommendation for student based on below details also the list of mentors with their experience is attached.
|
|
|
141 |
stream = client.text_generation(formatted_prompt, **generate_kwargs, stream=False, details=False, return_full_text=False)
|
142 |
return jsonify({"ans": stream})
|
143 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
144 |
|
145 |
if __name__ == '__main__':
|
146 |
app.run(debug=True)
|