-
Notifications
You must be signed in to change notification settings - Fork 20
Expand file tree
/
Copy pathapp.py
More file actions
210 lines (195 loc) · 7.21 KB
/
app.py
File metadata and controls
210 lines (195 loc) · 7.21 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
import sqlite3
import uuid
from flask import Flask, render_template, request, redirect, url_for, session, flash, g
from flask_socketio import SocketIO, send
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
DATABASE = 'market.db'
socketio = SocketIO(app)
# 데이터베이스 연결 관리: 요청마다 연결 생성 후 사용, 종료 시 close
def get_db():
db = getattr(g, '_database', None)
if db is None:
db = g._database = sqlite3.connect(DATABASE)
db.row_factory = sqlite3.Row # 결과를 dict처럼 사용하기 위함
return db
@app.teardown_appcontext
def close_connection(exception):
db = getattr(g, '_database', None)
if db is not None:
db.close()
# 테이블 생성 (최초 실행 시에만)
def init_db():
with app.app_context():
db = get_db()
cursor = db.cursor()
# 사용자 테이블 생성
cursor.execute("""
CREATE TABLE IF NOT EXISTS user (
id TEXT PRIMARY KEY,
username TEXT UNIQUE NOT NULL,
password TEXT NOT NULL,
bio TEXT
)
""")
# 상품 테이블 생성
cursor.execute("""
CREATE TABLE IF NOT EXISTS product (
id TEXT PRIMARY KEY,
title TEXT NOT NULL,
description TEXT NOT NULL,
price TEXT NOT NULL,
seller_id TEXT NOT NULL
)
""")
# 신고 테이블 생성
cursor.execute("""
CREATE TABLE IF NOT EXISTS report (
id TEXT PRIMARY KEY,
reporter_id TEXT NOT NULL,
target_id TEXT NOT NULL,
reason TEXT NOT NULL
)
""")
db.commit()
# 기본 라우트
@app.route('/')
def index():
if 'user_id' in session:
return redirect(url_for('dashboard'))
return render_template('index.html')
# 회원가입
@app.route('/register', methods=['GET', 'POST'])
def register():
if request.method == 'POST':
username = request.form['username']
password = request.form['password']
db = get_db()
cursor = db.cursor()
# 중복 사용자 체크
cursor.execute("SELECT * FROM user WHERE username = ?", (username,))
if cursor.fetchone() is not None:
flash('이미 존재하는 사용자명입니다.')
return redirect(url_for('register'))
user_id = str(uuid.uuid4())
cursor.execute("INSERT INTO user (id, username, password) VALUES (?, ?, ?)",
(user_id, username, password))
db.commit()
flash('회원가입이 완료되었습니다. 로그인 해주세요.')
return redirect(url_for('login'))
return render_template('register.html')
# 로그인
@app.route('/login', methods=['GET', 'POST'])
def login():
if request.method == 'POST':
username = request.form['username']
password = request.form['password']
db = get_db()
cursor = db.cursor()
cursor.execute("SELECT * FROM user WHERE username = ? AND password = ?", (username, password))
user = cursor.fetchone()
if user:
session['user_id'] = user['id']
flash('로그인 성공!')
return redirect(url_for('dashboard'))
else:
flash('아이디 또는 비밀번호가 올바르지 않습니다.')
return redirect(url_for('login'))
return render_template('login.html')
# 로그아웃
@app.route('/logout')
def logout():
session.pop('user_id', None)
flash('로그아웃되었습니다.')
return redirect(url_for('index'))
# 대시보드: 사용자 정보와 전체 상품 리스트 표시
@app.route('/dashboard')
def dashboard():
if 'user_id' not in session:
return redirect(url_for('login'))
db = get_db()
cursor = db.cursor()
# 현재 사용자 조회
cursor.execute("SELECT * FROM user WHERE id = ?", (session['user_id'],))
current_user = cursor.fetchone()
# 모든 상품 조회
cursor.execute("SELECT * FROM product")
all_products = cursor.fetchall()
return render_template('dashboard.html', products=all_products, user=current_user)
# 프로필 페이지: bio 업데이트 가능
@app.route('/profile', methods=['GET', 'POST'])
def profile():
if 'user_id' not in session:
return redirect(url_for('login'))
db = get_db()
cursor = db.cursor()
if request.method == 'POST':
bio = request.form.get('bio', '')
cursor.execute("UPDATE user SET bio = ? WHERE id = ?", (bio, session['user_id']))
db.commit()
flash('프로필이 업데이트되었습니다.')
return redirect(url_for('profile'))
cursor.execute("SELECT * FROM user WHERE id = ?", (session['user_id'],))
current_user = cursor.fetchone()
return render_template('profile.html', user=current_user)
# 상품 등록
@app.route('/product/new', methods=['GET', 'POST'])
def new_product():
if 'user_id' not in session:
return redirect(url_for('login'))
if request.method == 'POST':
title = request.form['title']
description = request.form['description']
price = request.form['price']
db = get_db()
cursor = db.cursor()
product_id = str(uuid.uuid4())
cursor.execute(
"INSERT INTO product (id, title, description, price, seller_id) VALUES (?, ?, ?, ?, ?)",
(product_id, title, description, price, session['user_id'])
)
db.commit()
flash('상품이 등록되었습니다.')
return redirect(url_for('dashboard'))
return render_template('new_product.html')
# 상품 상세보기
@app.route('/product/<product_id>')
def view_product(product_id):
db = get_db()
cursor = db.cursor()
cursor.execute("SELECT * FROM product WHERE id = ?", (product_id,))
product = cursor.fetchone()
if not product:
flash('상품을 찾을 수 없습니다.')
return redirect(url_for('dashboard'))
# 판매자 정보 조회
cursor.execute("SELECT * FROM user WHERE id = ?", (product['seller_id'],))
seller = cursor.fetchone()
return render_template('view_product.html', product=product, seller=seller)
# 신고하기
@app.route('/report', methods=['GET', 'POST'])
def report():
if 'user_id' not in session:
return redirect(url_for('login'))
if request.method == 'POST':
target_id = request.form['target_id']
reason = request.form['reason']
db = get_db()
cursor = db.cursor()
report_id = str(uuid.uuid4())
cursor.execute(
"INSERT INTO report (id, reporter_id, target_id, reason) VALUES (?, ?, ?, ?)",
(report_id, session['user_id'], target_id, reason)
)
db.commit()
flash('신고가 접수되었습니다.')
return redirect(url_for('dashboard'))
return render_template('report.html')
# 실시간 채팅: 클라이언트가 메시지를 보내면 전체 브로드캐스트
@socketio.on('send_message')
def handle_send_message_event(data):
data['message_id'] = str(uuid.uuid4())
send(data, broadcast=True)
if __name__ == '__main__':
init_db() # 앱 컨텍스트 내에서 테이블 생성
socketio.run(app, debug=True)