155 lines · 5.6 KB
1 -- gitfastr initial schema
2
3 -- Users
4 CREATE TABLE users (
5 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
6 username TEXT NOT NULL UNIQUE,
7 email TEXT NOT NULL UNIQUE,
8 password_hash TEXT NOT NULL,
9 display_name TEXT,
10 bio TEXT,
11 avatar_url TEXT,
12 is_admin INTEGER NOT NULL DEFAULT 0,
13 created_at TEXT NOT NULL DEFAULT (datetime('now')),
14 updated_at TEXT NOT NULL DEFAULT (datetime('now'))
15 );
16 CREATE INDEX idx_users_username ON users(username);
17
18 -- Personal Access Tokens
19 CREATE TABLE access_tokens (
20 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
21 user_id TEXT NOT NULL REFERENCES users(id) ON DELETE CASCADE,
22 name TEXT NOT NULL,
23 token_hash TEXT NOT NULL UNIQUE,
24 token_prefix TEXT NOT NULL,
25 scopes TEXT NOT NULL DEFAULT 'repo',
26 expires_at TEXT,
27 last_used_at TEXT,
28 created_at TEXT NOT NULL DEFAULT (datetime('now'))
29 );
30 CREATE INDEX idx_access_tokens_user ON access_tokens(user_id);
31 CREATE INDEX idx_access_tokens_hash ON access_tokens(token_hash);
32
33 -- Sessions (web UI)
34 CREATE TABLE sessions (
35 id TEXT PRIMARY KEY,
36 user_id TEXT NOT NULL REFERENCES users(id) ON DELETE CASCADE,
37 expires_at TEXT NOT NULL,
38 created_at TEXT NOT NULL DEFAULT (datetime('now'))
39 );
40 CREATE INDEX idx_sessions_user ON sessions(user_id);
41
42 -- Repositories
43 CREATE TABLE repositories (
44 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
45 owner_id TEXT NOT NULL REFERENCES users(id) ON DELETE CASCADE,
46 name TEXT NOT NULL,
47 description TEXT,
48 default_branch TEXT NOT NULL DEFAULT 'main',
49 is_private INTEGER NOT NULL DEFAULT 0,
50 fork_of TEXT REFERENCES repositories(id) ON DELETE SET NULL,
51 object_count INTEGER NOT NULL DEFAULT 0,
52 size_bytes INTEGER NOT NULL DEFAULT 0,
53 created_at TEXT NOT NULL DEFAULT (datetime('now')),
54 updated_at TEXT NOT NULL DEFAULT (datetime('now')),
55 UNIQUE(owner_id, name)
56 );
57 CREATE INDEX idx_repos_owner ON repositories(owner_id);
58
59 -- Refs (branches + tags)
60 CREATE TABLE refs (
61 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
62 repo_id TEXT NOT NULL REFERENCES repositories(id) ON DELETE CASCADE,
63 name TEXT NOT NULL,
64 sha TEXT NOT NULL,
65 is_symbolic INTEGER NOT NULL DEFAULT 0,
66 target_ref TEXT,
67 updated_at TEXT NOT NULL DEFAULT (datetime('now')),
68 UNIQUE(repo_id, name)
69 );
70 CREATE INDEX idx_refs_repo ON refs(repo_id);
71 CREATE INDEX idx_refs_repo_name ON refs(repo_id, name);
72
73 -- Repository collaborators
74 CREATE TABLE collaborators (
75 repo_id TEXT NOT NULL REFERENCES repositories(id) ON DELETE CASCADE,
76 user_id TEXT NOT NULL REFERENCES users(id) ON DELETE CASCADE,
77 permission TEXT NOT NULL DEFAULT 'read',
78 created_at TEXT NOT NULL DEFAULT (datetime('now')),
79 PRIMARY KEY (repo_id, user_id)
80 );
81
82 -- Merge Requests
83 CREATE TABLE merge_requests (
84 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
85 repo_id TEXT NOT NULL REFERENCES repositories(id) ON DELETE CASCADE,
86 number INTEGER NOT NULL,
87 title TEXT NOT NULL,
88 description TEXT,
89 author_id TEXT NOT NULL REFERENCES users(id),
90 state TEXT NOT NULL DEFAULT 'open',
91 source_branch TEXT NOT NULL,
92 target_branch TEXT NOT NULL,
93 source_sha TEXT,
94 merged_sha TEXT,
95 merged_by TEXT REFERENCES users(id),
96 created_at TEXT NOT NULL DEFAULT (datetime('now')),
97 updated_at TEXT NOT NULL DEFAULT (datetime('now')),
98 UNIQUE(repo_id, number)
99 );
100 CREATE INDEX idx_mr_repo ON merge_requests(repo_id);
101 CREATE INDEX idx_mr_author ON merge_requests(author_id);
102 CREATE INDEX idx_mr_state ON merge_requests(repo_id, state);
103
104 -- MR Comments
105 CREATE TABLE mr_comments (
106 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
107 mr_id TEXT NOT NULL REFERENCES merge_requests(id) ON DELETE CASCADE,
108 author_id TEXT NOT NULL REFERENCES users(id),
109 body TEXT NOT NULL,
110 file_path TEXT,
111 line_number INTEGER,
112 diff_side TEXT,
113 commit_sha TEXT,
114 parent_id TEXT REFERENCES mr_comments(id) ON DELETE CASCADE,
115 created_at TEXT NOT NULL DEFAULT (datetime('now')),
116 updated_at TEXT NOT NULL DEFAULT (datetime('now'))
117 );
118 CREATE INDEX idx_comments_mr ON mr_comments(mr_id);
119
120 -- MR Reviews
121 CREATE TABLE mr_reviews (
122 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
123 mr_id TEXT NOT NULL REFERENCES merge_requests(id) ON DELETE CASCADE,
124 reviewer_id TEXT NOT NULL REFERENCES users(id),
125 state TEXT NOT NULL,
126 body TEXT,
127 created_at TEXT NOT NULL DEFAULT (datetime('now'))
128 );
129 CREATE INDEX idx_reviews_mr ON mr_reviews(mr_id);
130
131 -- Webhooks
132 CREATE TABLE webhooks (
133 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
134 repo_id TEXT NOT NULL REFERENCES repositories(id) ON DELETE CASCADE,
135 url TEXT NOT NULL,
136 secret TEXT,
137 events TEXT NOT NULL DEFAULT 'push',
138 is_active INTEGER NOT NULL DEFAULT 1,
139 created_at TEXT NOT NULL DEFAULT (datetime('now'))
140 );
141 CREATE INDEX idx_webhooks_repo ON webhooks(repo_id);
142
143 -- Activity log
144 CREATE TABLE activity_log (
145 id TEXT PRIMARY KEY DEFAULT (lower(hex(randomblob(16)))),
146 repo_id TEXT REFERENCES repositories(id) ON DELETE CASCADE,
147 user_id TEXT REFERENCES users(id) ON DELETE SET NULL,
148 action TEXT NOT NULL,
149 details TEXT,
150 created_at TEXT NOT NULL DEFAULT (datetime('now'))
151 );
152 CREATE INDEX idx_activity_repo ON activity_log(repo_id);
153 CREATE INDEX idx_activity_user ON activity_log(user_id);
154 CREATE INDEX idx_activity_time ON activity_log(created_at);
155