forked from TiwariDivya25/DevConnect
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathSAFE-database-setup.sql
More file actions
266 lines (212 loc) · 10.7 KB
/
SAFE-database-setup.sql
File metadata and controls
266 lines (212 loc) · 10.7 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
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
-- ============================================================
-- DEVCONNECT DATABASE SCHEMA - SAFE VERSION
-- ============================================================
-- This version drops existing policies before creating new ones
-- Safe to run multiple times
-- ============================================================
-- 1. COMMUNITIES TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS communities (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
name TEXT NOT NULL UNIQUE,
description TEXT,
icon_url TEXT,
banner_url TEXT,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
ALTER TABLE communities ENABLE ROW LEVEL SECURITY;
-- Drop existing policies if they exist
DROP POLICY IF EXISTS "Communities are viewable by everyone" ON communities;
DROP POLICY IF EXISTS "Authenticated users can create communities" ON communities;
DROP POLICY IF EXISTS "Authenticated users can update communities" ON communities;
-- Create policies
CREATE POLICY "Communities are viewable by everyone" ON communities
FOR SELECT USING (true);
CREATE POLICY "Authenticated users can create communities" ON communities
FOR INSERT WITH CHECK (auth.role() = 'authenticated');
CREATE POLICY "Authenticated users can update communities" ON communities
FOR UPDATE USING (auth.role() = 'authenticated');
-- ============================================================
-- 2. COMMUNITY MEMBERS TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS community_members (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
community_id BIGINT NOT NULL REFERENCES communities(id) ON DELETE CASCADE,
user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
role TEXT DEFAULT 'member' CHECK (role IN ('admin', 'moderator', 'member')),
joined_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
UNIQUE(community_id, user_id)
);
CREATE INDEX IF NOT EXISTS idx_community_members_community_id ON community_members(community_id);
CREATE INDEX IF NOT EXISTS idx_community_members_user_id ON community_members(user_id);
ALTER TABLE community_members ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Community members are viewable by everyone" ON community_members;
DROP POLICY IF EXISTS "Users can join communities" ON community_members;
DROP POLICY IF EXISTS "Users can leave communities" ON community_members;
CREATE POLICY "Community members are viewable by everyone" ON community_members
FOR SELECT USING (true);
CREATE POLICY "Users can join communities" ON community_members
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can leave communities" ON community_members
FOR DELETE USING (auth.uid() = user_id);
-- ============================================================
-- 3. POSTS TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS posts (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
title TEXT NOT NULL,
content TEXT NOT NULL,
image_url TEXT,
avatar_url TEXT,
community_id BIGINT REFERENCES communities(id) ON DELETE SET NULL,
user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_posts_user_id ON posts(user_id);
CREATE INDEX IF NOT EXISTS idx_posts_community_id ON posts(community_id);
CREATE INDEX IF NOT EXISTS idx_posts_created_at ON posts(created_at DESC);
ALTER TABLE posts ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Posts are viewable by everyone" ON posts;
DROP POLICY IF EXISTS "Authenticated users can create posts" ON posts;
DROP POLICY IF EXISTS "Users can update own posts" ON posts;
DROP POLICY IF EXISTS "Users can delete own posts" ON posts;
CREATE POLICY "Posts are viewable by everyone" ON posts
FOR SELECT USING (true);
CREATE POLICY "Authenticated users can create posts" ON posts
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can update own posts" ON posts
FOR UPDATE USING (auth.uid() = user_id);
CREATE POLICY "Users can delete own posts" ON posts
FOR DELETE USING (auth.uid() = user_id);
-- ============================================================
-- 4. COMMENTS TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS comments (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
post_id BIGINT NOT NULL REFERENCES posts(id) ON DELETE CASCADE,
content TEXT NOT NULL,
author TEXT NOT NULL,
avatar_url TEXT,
user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
parent_comment_id BIGINT REFERENCES comments(id) ON DELETE CASCADE,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_comments_post_id ON comments(post_id);
CREATE INDEX IF NOT EXISTS idx_comments_user_id ON comments(user_id);
CREATE INDEX IF NOT EXISTS idx_comments_parent_id ON comments(parent_comment_id);
ALTER TABLE comments ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Comments are viewable by everyone" ON comments;
DROP POLICY IF EXISTS "Authenticated users can create comments" ON comments;
DROP POLICY IF EXISTS "Users can update own comments" ON comments;
DROP POLICY IF EXISTS "Users can delete own comments" ON comments;
CREATE POLICY "Comments are viewable by everyone" ON comments
FOR SELECT USING (true);
CREATE POLICY "Authenticated users can create comments" ON comments
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can update own comments" ON comments
FOR UPDATE USING (auth.uid() = user_id);
CREATE POLICY "Users can delete own comments" ON comments
FOR DELETE USING (auth.uid() = user_id);
-- ============================================================
-- 5. VOTES TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS votes (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
post_id BIGINT NOT NULL REFERENCES posts(id) ON DELETE CASCADE,
user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
vote INT DEFAULT 1,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
UNIQUE(post_id, user_id)
);
CREATE INDEX IF NOT EXISTS idx_votes_post_id ON votes(post_id);
CREATE INDEX IF NOT EXISTS idx_votes_user_id ON votes(user_id);
ALTER TABLE votes ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Votes are viewable by everyone" ON votes;
DROP POLICY IF EXISTS "Users can create votes" ON votes;
DROP POLICY IF EXISTS "Users can delete own votes" ON votes;
CREATE POLICY "Votes are viewable by everyone" ON votes
FOR SELECT USING (true);
CREATE POLICY "Users can create votes" ON votes
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can delete own votes" ON votes
FOR DELETE USING (auth.uid() = user_id);
-- ============================================================
-- 6. EVENTS TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS events (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
title TEXT NOT NULL,
description TEXT NOT NULL,
event_date TIMESTAMP WITH TIME ZONE NOT NULL,
location TEXT,
is_virtual BOOLEAN DEFAULT FALSE,
meeting_link TEXT,
max_attendees INTEGER,
image_url TEXT,
tags TEXT[],
organizer_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
community_id BIGINT REFERENCES communities(id) ON DELETE SET NULL,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_events_organizer_id ON events(organizer_id);
CREATE INDEX IF NOT EXISTS idx_events_community_id ON events(community_id);
CREATE INDEX IF NOT EXISTS idx_events_event_date ON events(event_date);
ALTER TABLE events ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Events are viewable by everyone" ON events;
DROP POLICY IF EXISTS "Authenticated users can create events" ON events;
DROP POLICY IF EXISTS "Organizers can update own events" ON events;
DROP POLICY IF EXISTS "Organizers can delete own events" ON events;
CREATE POLICY "Events are viewable by everyone" ON events
FOR SELECT USING (true);
CREATE POLICY "Authenticated users can create events" ON events
FOR INSERT WITH CHECK (auth.uid() = organizer_id);
CREATE POLICY "Organizers can update own events" ON events
FOR UPDATE USING (auth.uid() = organizer_id);
CREATE POLICY "Organizers can delete own events" ON events
FOR DELETE USING (auth.uid() = organizer_id);
-- ============================================================
-- 7. EVENT ATTENDEES TABLE
-- ============================================================
CREATE TABLE IF NOT EXISTS event_attendees (
id BIGINT PRIMARY KEY GENERATED ALWAYS AS IDENTITY,
event_id BIGINT NOT NULL REFERENCES events(id) ON DELETE CASCADE,
user_id UUID NOT NULL REFERENCES auth.users(id) ON DELETE CASCADE,
status TEXT DEFAULT 'attending' CHECK (status IN ('attending', 'maybe', 'not_attending')),
registered_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
UNIQUE(event_id, user_id)
);
CREATE INDEX IF NOT EXISTS idx_event_attendees_event_id ON event_attendees(event_id);
CREATE INDEX IF NOT EXISTS idx_event_attendees_user_id ON event_attendees(user_id);
ALTER TABLE event_attendees ENABLE ROW LEVEL SECURITY;
DROP POLICY IF EXISTS "Event attendees are viewable by everyone" ON event_attendees;
DROP POLICY IF EXISTS "Users can register for events" ON event_attendees;
DROP POLICY IF EXISTS "Users can update own registration" ON event_attendees;
DROP POLICY IF EXISTS "Users can delete own registration" ON event_attendees;
CREATE POLICY "Event attendees are viewable by everyone" ON event_attendees
FOR SELECT USING (true);
CREATE POLICY "Users can register for events" ON event_attendees
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can update own registration" ON event_attendees
FOR UPDATE USING (auth.uid() = user_id);
CREATE POLICY "Users can delete own registration" ON event_attendees
FOR DELETE USING (auth.uid() = user_id);
-- ============================================================
-- VERIFICATION
-- ============================================================
SELECT
'✅ Database setup complete! All tables created successfully.' as message,
COUNT(*) as table_count
FROM information_schema.tables
WHERE table_schema = 'public'
AND table_name IN ('communities', 'community_members', 'posts', 'comments', 'votes', 'events', 'event_attendees');
-- List all created tables
SELECT
table_name,
(SELECT COUNT(*) FROM information_schema.columns WHERE table_name = t.table_name AND table_schema = 'public') as column_count
FROM information_schema.tables t
WHERE table_schema = 'public'
AND table_name IN ('communities', 'community_members', 'posts', 'comments', 'votes', 'events', 'event_attendees')
ORDER BY table_name;