From d63d6fc57ec6108e517413300ce7c1afb7c5dcbd Mon Sep 17 00:00:00 2001 From: Anirudh Oppiliappan Date: Mon, 15 Sep 2025 16:58:52 +0300 Subject: [PATCH] appview/db: return ids in a few places Change-Id: wxwnvpytuuuxxwslmtrymxomvtkrtrws Signed-off-by: Anirudh Oppiliappan --- appview/db/db.go | 7 ------ appview/db/pulls.go | 13 +++++++++- appview/db/repos.go | 42 +++++++++++++++++++++++++++----- appview/notify/db/db.go | 54 ++++++++++++++++++++--------------------- appview/state/state.go | 1 + 5 files changed, 76 insertions(+), 41 deletions(-) diff --git a/appview/db/db.go b/appview/db/db.go index bb6a52af..a4b39560 100644 --- a/appview/db/db.go +++ b/appview/db/db.go @@ -817,13 +817,6 @@ func Make(dbPath string) (*DB, error) { _, err := tx.Exec(` alter table spindles add column needs_upgrade integer not null default 0; `) - if err != nil { - return err - } - - _, err = tx.Exec(` - update spindles set needs_upgrade = 1; - `) return err }) diff --git a/appview/db/pulls.go b/appview/db/pulls.go index cdddd1f0..aad64fdc 100644 --- a/appview/db/pulls.go +++ b/appview/db/pulls.go @@ -55,7 +55,7 @@ func NewPull(tx *sql.Tx, pull *models.Pull) error { parentChangeId = &pull.ParentChangeId } - _, err = tx.Exec( + result, err := tx.Exec( ` insert into pulls ( repo_at, owner_did, pull_id, title, target_branch, body, rkey, state, source_branch, source_repo_at, stack_id, change_id, parent_change_id @@ -79,6 +79,13 @@ func NewPull(tx *sql.Tx, pull *models.Pull) error { return err } + // Set the database primary key ID + id, err := result.LastInsertId() + if err != nil { + return err + } + pull.ID = int(id) + _, err = tx.Exec(` insert into pull_submissions (pull_id, repo_at, round_number, patch, source_rev) values (?, ?, ?, ?, ?) @@ -121,6 +128,7 @@ func GetPullsWithLimit(e Execer, limit int, filters ...filter) ([]*models.Pull, query := fmt.Sprintf(` select + id, owner_did, repo_at, pull_id, @@ -154,6 +162,7 @@ func GetPullsWithLimit(e Execer, limit int, filters ...filter) ([]*models.Pull, var createdAt string var sourceBranch, sourceRepoAt, stackId, changeId, parentChangeId sql.NullString err := rows.Scan( + &pull.ID, &pull.OwnerDid, &pull.RepoAt, &pull.PullId, @@ -325,6 +334,7 @@ func GetPulls(e Execer, filters ...filter) ([]*models.Pull, error) { func GetPull(e Execer, repoAt syntax.ATURI, pullId int) (*models.Pull, error) { query := ` select + id, owner_did, pull_id, created, @@ -350,6 +360,7 @@ func GetPull(e Execer, repoAt syntax.ATURI, pullId int) (*models.Pull, error) { var createdAt string var sourceBranch, sourceRepoAt, stackId, changeId, parentChangeId sql.NullString err := row.Scan( + &pull.ID, &pull.OwnerDid, &pull.PullId, &createdAt, diff --git a/appview/db/repos.go b/appview/db/repos.go index 48a94c74..27a88b66 100644 --- a/appview/db/repos.go +++ b/appview/db/repos.go @@ -10,9 +10,37 @@ import ( "time" "github.com/bluesky-social/indigo/atproto/syntax" + securejoin "github.com/cyphar/filepath-securejoin" + "tangled.org/core/api/tangled" "tangled.org/core/appview/models" ) +type Repo struct { + Id int64 + Did string + Name string + Knot string + Rkey string + Created time.Time + Description string + Spindle string + + // optionally, populate this when querying for reverse mappings + RepoStats *models.RepoStats + + // optional + Source string +} + +func (r Repo) RepoAt() syntax.ATURI { + return syntax.ATURI(fmt.Sprintf("at://%s/%s/%s", r.Did, tangled.RepoNSID, r.Rkey)) +} + +func (r Repo) DidSlashRepo() string { + p, _ := securejoin.SecureJoin(r.Did, r.Name) + return p +} + func GetRepos(e Execer, limit int, filters ...filter) ([]models.Repo, error) { repoMap := make(map[syntax.ATURI]*models.Repo) @@ -35,6 +63,7 @@ func GetRepos(e Execer, limit int, filters ...filter) ([]models.Repo, error) { repoQuery := fmt.Sprintf( `select + id, did, name, knot, @@ -63,6 +92,7 @@ func GetRepos(e Execer, limit int, filters ...filter) ([]models.Repo, error) { var description, source, spindle sql.NullString err := rows.Scan( + &repo.Id, &repo.Did, &repo.Name, &repo.Knot, @@ -327,10 +357,10 @@ func GetRepoByAtUri(e Execer, atUri string) (*models.Repo, error) { var repo models.Repo var nullableDescription sql.NullString - row := e.QueryRow(`select did, name, knot, created, rkey, description from repos where at_uri = ?`, atUri) + row := e.QueryRow(`select id, did, name, knot, created, rkey, description from repos where at_uri = ?`, atUri) var createdAt string - if err := row.Scan(&repo.Did, &repo.Name, &repo.Knot, &createdAt, &repo.Rkey, &nullableDescription); err != nil { + if err := row.Scan(&repo.Id, &repo.Did, &repo.Name, &repo.Knot, &createdAt, &repo.Rkey, &nullableDescription); err != nil { return nil, err } createdAtTime, _ := time.Parse(time.RFC3339, createdAt) @@ -386,7 +416,7 @@ func GetForksByDid(e Execer, did string) ([]models.Repo, error) { var repos []models.Repo rows, err := e.Query( - `select distinct r.did, r.name, r.knot, r.rkey, r.description, r.created, r.source + `select distinct r.id, r.did, r.name, r.knot, r.rkey, r.description, r.created, r.source from repos r left join collaborators c on r.at_uri = c.repo_at where (r.did = ? or c.subject_did = ?) @@ -406,7 +436,7 @@ func GetForksByDid(e Execer, did string) ([]models.Repo, error) { var nullableDescription sql.NullString var nullableSource sql.NullString - err := rows.Scan(&repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &nullableSource) + err := rows.Scan(&repo.Id, &repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &nullableSource) if err != nil { return nil, err } @@ -443,13 +473,13 @@ func GetForkByDid(e Execer, did string, name string) (*models.Repo, error) { var nullableSource sql.NullString row := e.QueryRow( - `select did, name, knot, rkey, description, created, source + `select id, did, name, knot, rkey, description, created, source from repos where did = ? and name = ? and source is not null and source != ''`, did, name, ) - err := row.Scan(&repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &nullableSource) + err := row.Scan(&repo.Id, &repo.Did, &repo.Name, &repo.Knot, &repo.Rkey, &nullableDescription, &createdAt, &nullableSource) if err != nil { return nil, err } diff --git a/appview/notify/db/db.go b/appview/notify/db/db.go index 3401e9f0..ef75550e 100644 --- a/appview/notify/db/db.go +++ b/appview/notify/db/db.go @@ -4,9 +4,10 @@ import ( "context" "log" - "tangled.sh/tangled.sh/core/appview/db" - "tangled.sh/tangled.sh/core/appview/notify" - "tangled.sh/tangled.sh/core/idresolver" + "tangled.org/core/appview/db" + "tangled.org/core/appview/models" + "tangled.org/core/appview/notify" + "tangled.org/core/idresolver" ) type databaseNotifier struct { @@ -23,11 +24,11 @@ func NewDatabaseNotifier(database *db.DB, resolver *idresolver.Resolver) notify. var _ notify.Notifier = &databaseNotifier{} -func (n *databaseNotifier) NewRepo(ctx context.Context, repo *db.Repo) { +func (n *databaseNotifier) NewRepo(ctx context.Context, repo *models.Repo) { // no-op for now } -func (n *databaseNotifier) NewStar(ctx context.Context, star *db.Star) { +func (n *databaseNotifier) NewStar(ctx context.Context, star *models.Star) { var err error repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(star.RepoAt))) if err != nil { @@ -61,9 +62,8 @@ func (n *databaseNotifier) NewStar(ctx context.Context, star *db.Star) { Type: models.NotificationTypeRepoStarred, EntityType: "repo", EntityId: string(star.RepoAt), - RepoId: &repo.ID, + RepoId: &repo.Id, } - err = n.db.CreateNotification(ctx, notification) if err != nil { log.Printf("NewStar: failed to create notification: %v", err) @@ -71,11 +71,11 @@ func (n *databaseNotifier) NewStar(ctx context.Context, star *db.Star) { } } -func (n *databaseNotifier) DeleteStar(ctx context.Context, star *db.Star) { +func (n *databaseNotifier) DeleteStar(ctx context.Context, star *models.Star) { // no-op } -func (n *databaseNotifier) NewIssue(ctx context.Context, issue *db.Issue) { +func (n *databaseNotifier) NewIssue(ctx context.Context, issue *models.Issue) { repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(issue.RepoAt))) if err != nil { log.Printf("NewIssue: failed to get repos: %v", err) @@ -106,7 +106,7 @@ func (n *databaseNotifier) NewIssue(ctx context.Context, issue *db.Issue) { Type: models.NotificationTypeIssueCreated, EntityType: "issue", EntityId: string(issue.AtUri()), - RepoId: &repo.ID, + RepoId: &repo.Id, IssueId: &issue.Id, } @@ -117,7 +117,7 @@ func (n *databaseNotifier) NewIssue(ctx context.Context, issue *db.Issue) { } } -func (n *databaseNotifier) NewIssueComment(ctx context.Context, comment *db.IssueComment) { +func (n *databaseNotifier) NewIssueComment(ctx context.Context, comment *models.IssueComment) { issues, err := db.GetIssues(n.db, db.FilterEq("at_uri", comment.IssueAt)) if err != nil { log.Printf("NewIssueComment: failed to get issues: %v", err) @@ -170,7 +170,7 @@ func (n *databaseNotifier) NewIssueComment(ctx context.Context, comment *db.Issu Type: models.NotificationTypeIssueCommented, EntityType: "issue", EntityId: string(issue.AtUri()), - RepoId: &repo.ID, + RepoId: &repo.Id, IssueId: &issue.Id, } @@ -181,7 +181,7 @@ func (n *databaseNotifier) NewIssueComment(ctx context.Context, comment *db.Issu } } -func (n *databaseNotifier) NewFollow(ctx context.Context, follow *db.Follow) { +func (n *databaseNotifier) NewFollow(ctx context.Context, follow *models.Follow) { prefs, err := n.db.GetNotificationPreferences(ctx, follow.SubjectDid) if err != nil { log.Printf("NewFollow: failed to get notification preferences for %s: %v", follow.SubjectDid, err) @@ -206,11 +206,11 @@ func (n *databaseNotifier) NewFollow(ctx context.Context, follow *db.Follow) { } } -func (n *databaseNotifier) DeleteFollow(ctx context.Context, follow *db.Follow) { +func (n *databaseNotifier) DeleteFollow(ctx context.Context, follow *models.Follow) { // no-op } -func (n *databaseNotifier) NewPull(ctx context.Context, pull *db.Pull) { +func (n *databaseNotifier) NewPull(ctx context.Context, pull *models.Pull) { repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(pull.RepoAt))) if err != nil { log.Printf("NewPull: failed to get repos: %v", err) @@ -241,7 +241,7 @@ func (n *databaseNotifier) NewPull(ctx context.Context, pull *db.Pull) { Type: models.NotificationTypePullCreated, EntityType: "pull", EntityId: string(pull.RepoAt), - RepoId: &repo.ID, + RepoId: &repo.Id, PullId: func() *int64 { id := int64(pull.ID); return &id }(), } @@ -252,7 +252,7 @@ func (n *databaseNotifier) NewPull(ctx context.Context, pull *db.Pull) { } } -func (n *databaseNotifier) NewPullComment(ctx context.Context, comment *db.PullComment) { +func (n *databaseNotifier) NewPullComment(ctx context.Context, comment *models.PullComment) { pulls, err := db.GetPulls(n.db, db.FilterEq("repo_at", comment.RepoAt), db.FilterEq("pull_id", comment.PullId)) @@ -306,7 +306,7 @@ func (n *databaseNotifier) NewPullComment(ctx context.Context, comment *db.PullC Type: models.NotificationTypePullCommented, EntityType: "pull", EntityId: comment.RepoAt, - RepoId: &repo.ID, + RepoId: &repo.Id, PullId: func() *int64 { id := int64(pull.ID); return &id }(), } @@ -317,7 +317,7 @@ func (n *databaseNotifier) NewPullComment(ctx context.Context, comment *db.PullC } } -func (n *databaseNotifier) UpdateProfile(ctx context.Context, profile *db.Profile) { +func (n *databaseNotifier) UpdateProfile(ctx context.Context, profile *models.Profile) { // no-op } @@ -325,15 +325,15 @@ func (n *databaseNotifier) DeleteString(ctx context.Context, did, rkey string) { // no-op } -func (n *databaseNotifier) EditString(ctx context.Context, string *db.String) { +func (n *databaseNotifier) EditString(ctx context.Context, string *models.String) { // no-op } -func (n *databaseNotifier) NewString(ctx context.Context, string *db.String) { +func (n *databaseNotifier) NewString(ctx context.Context, string *models.String) { // no-op } -func (n *databaseNotifier) NewIssueClosed(ctx context.Context, issue *db.Issue) { +func (n *databaseNotifier) NewIssueClosed(ctx context.Context, issue *models.Issue) { // Get repo details repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(issue.RepoAt))) if err != nil { @@ -367,7 +367,7 @@ func (n *databaseNotifier) NewIssueClosed(ctx context.Context, issue *db.Issue) Type: models.NotificationTypeIssueClosed, EntityType: "issue", EntityId: string(issue.AtUri()), - RepoId: &repo.ID, + RepoId: &repo.Id, IssueId: &issue.Id, } @@ -378,7 +378,7 @@ func (n *databaseNotifier) NewIssueClosed(ctx context.Context, issue *db.Issue) } } -func (n *databaseNotifier) NewPullMerged(ctx context.Context, pull *db.Pull) { +func (n *databaseNotifier) NewPullMerged(ctx context.Context, pull *models.Pull) { // Get repo details repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(pull.RepoAt))) if err != nil { @@ -412,7 +412,7 @@ func (n *databaseNotifier) NewPullMerged(ctx context.Context, pull *db.Pull) { Type: models.NotificationTypePullMerged, EntityType: "pull", EntityId: string(pull.RepoAt), - RepoId: &repo.ID, + RepoId: &repo.Id, PullId: func() *int64 { id := int64(pull.ID); return &id }(), } @@ -423,7 +423,7 @@ func (n *databaseNotifier) NewPullMerged(ctx context.Context, pull *db.Pull) { } } -func (n *databaseNotifier) NewPullClosed(ctx context.Context, pull *db.Pull) { +func (n *databaseNotifier) NewPullClosed(ctx context.Context, pull *models.Pull) { // Get repo details repos, err := db.GetRepos(n.db, 1, db.FilterEq("at_uri", string(pull.RepoAt))) if err != nil { @@ -457,7 +457,7 @@ func (n *databaseNotifier) NewPullClosed(ctx context.Context, pull *db.Pull) { Type: models.NotificationTypePullClosed, EntityType: "pull", EntityId: string(pull.RepoAt), - RepoId: &repo.ID, + RepoId: &repo.Id, PullId: func() *int64 { id := int64(pull.ID); return &id }(), } diff --git a/appview/state/state.go b/appview/state/state.go index 4ea95be6..cc023855 100644 --- a/appview/state/state.go +++ b/appview/state/state.go @@ -25,6 +25,7 @@ import ( "tangled.org/core/appview/db" "tangled.org/core/appview/models" "tangled.org/core/appview/notify" + dbnotify "tangled.org/core/appview/notify/db" phnotify "tangled.org/core/appview/notify/posthog" "tangled.org/core/appview/oauth" "tangled.org/core/appview/pages" -- 2.43.0