forked from tangled.org/core
this repo has no description
1package db 2 3import ( 4 "database/sql" 5 "time" 6) 7 8type Repo struct { 9 Did string 10 Name string 11 Knot string 12 Rkey string 13 Created time.Time 14 AtUri string 15 Description string 16 17 // optionally, populate this when querying for reverse mappings 18 RepoStats *RepoStats 19} 20 21func GetAllRepos(e Execer, limit int) ([]Repo, error) { 22 var repos []Repo 23 24 rows, err := e.Query( 25 `select did, name, knot, rkey, description, created 26 from repos 27 order by created desc 28 limit ? 29 `, 30 limit, 31 ) 32 if err != nil { 33 return nil, err 34 } 35 defer rows.Close() 36 37 for rows.Next() { 38 var repo Repo 39 err := scanRepo( 40 rows, &repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &repo.Description, &repo.Created, 41 ) 42 if err != nil { 43 return nil, err 44 } 45 repos = append(repos, repo) 46 } 47 48 if err := rows.Err(); err != nil { 49 return nil, err 50 } 51 52 return repos, nil 53} 54 55func GetAllReposByDid(e Execer, did string) ([]Repo, error) { 56 var repos []Repo 57 58 rows, err := e.Query( 59 `select 60 r.did, 61 r.name, 62 r.knot, 63 r.rkey, 64 r.description, 65 r.created, 66 count(s.id) as star_count 67 from 68 repos r 69 left join 70 stars s on r.at_uri = s.repo_at 71 where 72 r.did = ? 73 group by 74 r.at_uri`, did) 75 if err != nil { 76 return nil, err 77 } 78 defer rows.Close() 79 80 for rows.Next() { 81 var repo Repo 82 var repoStats RepoStats 83 var createdAt string 84 var nullableDescription sql.NullString 85 86 err := rows.Scan(&repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &repoStats.StarCount) 87 if err != nil { 88 return nil, err 89 } 90 91 if nullableDescription.Valid { 92 repo.Description = nullableDescription.String 93 } else { 94 repo.Description = "" 95 } 96 97 createdAtTime, err := time.Parse(time.RFC3339, createdAt) 98 if err != nil { 99 repo.Created = time.Now() 100 } else { 101 repo.Created = createdAtTime 102 } 103 104 repo.RepoStats = &repoStats 105 106 repos = append(repos, repo) 107 } 108 109 if err := rows.Err(); err != nil { 110 return nil, err 111 } 112 113 return repos, nil 114} 115 116func GetRepo(e Execer, did, name string) (*Repo, error) { 117 var repo Repo 118 var nullableDescription sql.NullString 119 120 row := e.QueryRow(`select did, name, knot, created, at_uri, description from repos where did = ? and name = ?`, did, name) 121 122 var createdAt string 123 if err := row.Scan(&repo.Did, &repo.Name, &repo.Knot, &createdAt, &repo.AtUri, &nullableDescription); err != nil { 124 return nil, err 125 } 126 createdAtTime, _ := time.Parse(time.RFC3339, createdAt) 127 repo.Created = createdAtTime 128 129 if nullableDescription.Valid { 130 repo.Description = nullableDescription.String 131 } else { 132 repo.Description = "" 133 } 134 135 return &repo, nil 136} 137 138func GetRepoByAtUri(e Execer, atUri string) (*Repo, error) { 139 var repo Repo 140 var nullableDescription sql.NullString 141 142 row := e.QueryRow(`select did, name, knot, created, at_uri, description from repos where at_uri = ?`, atUri) 143 144 var createdAt string 145 if err := row.Scan(&repo.Did, &repo.Name, &repo.Knot, &createdAt, &repo.AtUri, &nullableDescription); err != nil { 146 return nil, err 147 } 148 createdAtTime, _ := time.Parse(time.RFC3339, createdAt) 149 repo.Created = createdAtTime 150 151 if nullableDescription.Valid { 152 repo.Description = nullableDescription.String 153 } else { 154 repo.Description = "" 155 } 156 157 return &repo, nil 158} 159 160func AddRepo(e Execer, repo *Repo) error { 161 _, err := e.Exec( 162 `insert into repos 163 (did, name, knot, rkey, at_uri, description) 164 values (?, ?, ?, ?, ?, ?)`, 165 repo.Did, repo.Name, repo.Knot, repo.Rkey, repo.AtUri, repo.Description, 166 ) 167 return err 168} 169 170func RemoveRepo(e Execer, did, name, rkey string) error { 171 _, err := e.Exec(`delete from repos where did = ? and name = ? and rkey = ?`, did, name, rkey) 172 return err 173} 174 175func AddCollaborator(e Execer, collaborator, repoOwnerDid, repoName, repoKnot string) error { 176 _, err := e.Exec( 177 `insert into collaborators (did, repo) 178 values (?, (select id from repos where did = ? and name = ? and knot = ?));`, 179 collaborator, repoOwnerDid, repoName, repoKnot) 180 return err 181} 182 183func UpdateDescription(e Execer, repoAt, newDescription string) error { 184 _, err := e.Exec( 185 `update repos set description = ? where at_uri = ?`, newDescription, repoAt) 186 return err 187} 188 189func CollaboratingIn(e Execer, collaborator string) ([]Repo, error) { 190 var repos []Repo 191 192 rows, err := e.Query( 193 `select 194 r.did, r.name, r.knot, r.rkey, r.description, r.created, count(s.id) as star_count 195 from 196 repos r 197 join 198 collaborators c on r.id = c.repo 199 left join 200 stars s on r.at_uri = s.repo_at 201 where 202 c.did = ? 203 group by 204 r.id;`, collaborator) 205 if err != nil { 206 return nil, err 207 } 208 defer rows.Close() 209 210 for rows.Next() { 211 var repo Repo 212 var repoStats RepoStats 213 var createdAt string 214 var nullableDescription sql.NullString 215 216 err := rows.Scan(&repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &repoStats.StarCount) 217 if err != nil { 218 return nil, err 219 } 220 221 if nullableDescription.Valid { 222 repo.Description = nullableDescription.String 223 } else { 224 repo.Description = "" 225 } 226 227 createdAtTime, err := time.Parse(time.RFC3339, createdAt) 228 if err != nil { 229 repo.Created = time.Now() 230 } else { 231 repo.Created = createdAtTime 232 } 233 234 repo.RepoStats = &repoStats 235 236 repos = append(repos, repo) 237 } 238 239 if err := rows.Err(); err != nil { 240 return nil, err 241 } 242 243 return repos, nil 244} 245 246type RepoStats struct { 247 StarCount int 248 IssueCount IssueCount 249 PullCount PullCount 250} 251 252func scanRepo(rows *sql.Rows, did, name, knot, rkey, description *string, created *time.Time) error { 253 var createdAt string 254 var nullableDescription sql.NullString 255 if err := rows.Scan(did, name, knot, rkey, &nullableDescription, &createdAt); err != nil { 256 return err 257 } 258 259 if nullableDescription.Valid { 260 *description = nullableDescription.String 261 } else { 262 *description = "" 263 } 264 265 createdAtTime, err := time.Parse(time.RFC3339, createdAt) 266 if err != nil { 267 *created = time.Now() 268 } else { 269 *created = createdAtTime 270 } 271 272 return nil 273}