/
ch6_database.py
executable file
·148 lines (111 loc) · 3.64 KB
/
ch6_database.py
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
from flask import Flask, jsonify, request
from flask.json import JSONEncoder
from sqlalchemy import create_engine, text
class CustomJSONEncoder(JSONEncoder):
def default(self, obj):
if isinstance(obj, set):
return list(obj)
return JSONEncoder.default(self, obj)
def get_user(user_id):
query = """
SELECT id, name, email, profile FROM users WHERE id = :user_id
"""
user = current_app.database.execute(text(query), {"user_id": user_id}).fetchone()
return (
{"id": user["id"], "name": user["name"], "email": user["email"], "profile": user["profile"]}
if user
else None
)
def insert_user(user):
query = """
INSERT INTO users (
name, email, profile, hashed_password
) VALUE (
:name,
:email,
:profile,
:password
)
"""
return current_app.database.execute(text(query), user).lastrowid
def insert_tweet(user_tweet):
query = """
INSERT INTO tweets (
user_id,
tweet
) VALUE (
:id,
:tweet
)
"""
return current_app.database.execute(text(query), user_tweet).rowcount
def insert_follow(user_follow):
query = """
INSERT INTO users_follow_list (
user_id,
follow_user_id
) VALUE (
:id,
:follow
)
"""
return current_app.database.execute(text(query), user_follow).rowcount
def remove_follow(user_unfollow):
query = """
DELETE FROM users_follow_list
WHERE user_id = :id
AND follow_user_id = :unfollow
"""
return current_app.database.execute(text(query), user_unfollow).rowcount
def get_timeline(user_id):
query = """
SELECT
t.user_id,
t.tweet
FROM tweets t
LEFT JOIN users_follow_list ufl ON ufl.user_id = :user_id
WHERE t.user_id = :user_id
OR t.user_id = ufl.follow_user_id
"""
timeline = current_app.database.execute(text(query), {"user_id": user_id}).fetchall()
return [{"user_id": tweet["user_id"], "tweet": tweet["tweet"]} for tweet in timeline]
def create_app(test_config=None):
app = Flask(__name__)
if test_config is None:
app.config.from_pyfile("dbconfig.py")
else:
app.config.update(test_config)
database = create_engine(app.config["DB_URL"], encoding="UTF-8", max_overflow=0)
app.database = database
@app.route("/sign-up", methods=["POST"])
def sign_up():
print(request.json)
new_user = request.json
new_user_id = insert_user(new_user)
new_user = get_user(new_user_id)
return jsonify(new_user)
@app.route("/tweet", methods=["POST"])
def tweet():
user_tweet = request.json
tweet = user_tweet["tweet"]
if len(tweet) > 300:
return "300자를 초과하였습니다.", 400
insert_tweet(user_tweet)
return "트윗이 등록되었습니다.", 200
@app.route("/follow", methods=["POST"])
def follow():
payload = request.json
insert_follow(payload)
return "팔로워가 등록되었습니다.", 200
@app.route("/unfollow", methods=["POST"])
def unfollow():
payload = request.json
remove_follow(payload)
return "팔로워가 삭제되었습니다.", 200
@app.route("/timeline/<int:user_id>", methods=["GET"])
def timeline(user_id):
return jsonify({"user_id": user_id, "timeline": get_timeline(user_id)})
return app
current_app = create_app()
if __name__ == "__main__":
current_app.run(debug=True, host="0.0.0.0")