Implement sending follow activities
I moved around a lot of files to fix import cyclespull/20391/head
parent
e78dd699de
commit
f133e9ca11
|
@ -17,7 +17,7 @@ import (
|
|||
|
||||
// Create a comment
|
||||
func Comment(ctx context.Context, note *ap.Note) error {
|
||||
actorUser, err := personIRIToUser(ctx, note.AttributedTo.GetLink())
|
||||
actorUser, err := PersonIRIToUser(ctx, note.AttributedTo.GetLink())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
|
@ -17,14 +17,14 @@ import (
|
|||
func Follow(ctx context.Context, follow ap.Follow) error {
|
||||
// Actor is the user performing the follow
|
||||
actorIRI := follow.Actor.GetLink()
|
||||
actorUser, err := personIRIToUser(ctx, actorIRI)
|
||||
actorUser, err := PersonIRIToUser(ctx, actorIRI)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Object is the user being followed
|
||||
objectIRI := follow.Object.GetLink()
|
||||
objectUser, err := personIRIToUser(ctx, objectIRI)
|
||||
objectUser, err := PersonIRIToUser(ctx, objectIRI)
|
||||
// Must be a local user
|
||||
if err != nil || strings.Contains(objectUser.Name, "@") {
|
||||
return err
|
||||
|
@ -48,14 +48,14 @@ func Unfollow(ctx context.Context, unfollow ap.Undo) error {
|
|||
follow := unfollow.Object.(*ap.Follow)
|
||||
// Actor is the user performing the undo follow
|
||||
actorIRI := follow.Actor.GetLink()
|
||||
actorUser, err := personIRIToUser(ctx, actorIRI)
|
||||
actorUser, err := PersonIRIToUser(ctx, actorIRI)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Object is the user being unfollowed
|
||||
objectIRI := follow.Object.GetLink()
|
||||
objectUser, err := personIRIToUser(ctx, objectIRI)
|
||||
objectUser, err := PersonIRIToUser(ctx, objectIRI)
|
||||
// Must be a local user
|
||||
if err != nil || strings.Contains(objectUser.Name, "@") {
|
||||
return err
|
||||
|
|
|
@ -52,7 +52,7 @@ func ReceiveFork(ctx context.Context, create ap.Create) error {
|
|||
|
||||
repository := create.Object.(*forgefed.Repository)
|
||||
|
||||
actor, err := personIRIToUser(ctx, create.Actor.GetLink())
|
||||
actor, err := PersonIRIToUser(ctx, create.Actor.GetLink())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -62,7 +62,7 @@ func ReceiveFork(ctx context.Context, create ap.Create) error {
|
|||
|
||||
// Create the fork
|
||||
repoIRI := repository.GetLink()
|
||||
username, reponame, err := repositoryIRIToName(repoIRI)
|
||||
username, reponame, err := RepositoryIRIToName(repoIRI)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
|
@ -17,7 +17,7 @@ import (
|
|||
)
|
||||
|
||||
// Returns the username corresponding to a Person actor IRI
|
||||
func personIRIToName(personIRI ap.IRI) (string, error) {
|
||||
func PersonIRIToName(personIRI ap.IRI) (string, error) {
|
||||
personIRISplit := strings.Split(personIRI.String(), "/")
|
||||
if len(personIRISplit) < 3 {
|
||||
return "", errors.New("Not a Person actor IRI")
|
||||
|
@ -35,8 +35,8 @@ func personIRIToName(personIRI ap.IRI) (string, error) {
|
|||
}
|
||||
|
||||
// Returns the user corresponding to a Person actor IRI
|
||||
func personIRIToUser(ctx context.Context, personIRI ap.IRI) (*user_model.User, error) {
|
||||
name, err := personIRIToName(personIRI)
|
||||
func PersonIRIToUser(ctx context.Context, personIRI ap.IRI) (*user_model.User, error) {
|
||||
name, err := PersonIRIToName(personIRI)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ func personIRIToUser(ctx context.Context, personIRI ap.IRI) (*user_model.User, e
|
|||
}
|
||||
|
||||
// Returns the owner and name corresponding to a Repository actor IRI
|
||||
func repositoryIRIToName(repoIRI ap.IRI) (string, string, error) {
|
||||
func RepositoryIRIToName(repoIRI ap.IRI) (string, string, error) {
|
||||
repoIRISplit := strings.Split(repoIRI.String(), "/")
|
||||
if len(repoIRISplit) < 5 {
|
||||
return "", "", errors.New("Not a Repository actor IRI")
|
||||
|
@ -68,8 +68,8 @@ func repositoryIRIToName(repoIRI ap.IRI) (string, string, error) {
|
|||
}
|
||||
|
||||
// Returns the repository corresponding to a Repository actor IRI
|
||||
func repositoryIRIToRepository(ctx context.Context, repoIRI ap.IRI) (*repo_model.Repository, error) {
|
||||
username, reponame, err := repositoryIRIToName(repoIRI)
|
||||
func RepositoryIRIToRepository(ctx context.Context, repoIRI ap.IRI) (*repo_model.Repository, error) {
|
||||
username, reponame, err := RepositoryIRIToName(repoIRI)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
|
|
@ -18,7 +18,7 @@ import (
|
|||
func PullRequest(ctx context.Context, ticket *forgefed.Ticket) error {
|
||||
// TODO: Clean this up
|
||||
|
||||
actorUser, err := personIRIToUser(ctx, ticket.AttributedTo.GetLink())
|
||||
actorUser, err := PersonIRIToUser(ctx, ticket.AttributedTo.GetLink())
|
||||
if err != nil {
|
||||
log.Warn("Couldn't find ticket actor user", err)
|
||||
}
|
||||
|
|
|
@ -16,7 +16,7 @@ import (
|
|||
// Create a new federated repo from a Repository object
|
||||
func FederatedRepoNew(ctx context.Context, repository *forgefed.Repository) error {
|
||||
ownerIRI := repository.AttributedTo.GetLink()
|
||||
user, err := personIRIToUser(ctx, ownerIRI)
|
||||
user, err := PersonIRIToUser(ctx, ownerIRI)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -26,7 +26,6 @@ func FederatedRepoNew(ctx context.Context, repository *forgefed.Repository) erro
|
|||
return nil
|
||||
}
|
||||
|
||||
|
||||
repo, err := repo_service.CreateRepository(user, user, repo_module.CreateRepoOptions{
|
||||
Name: repository.Name.String(),
|
||||
})
|
||||
|
@ -36,7 +35,7 @@ func FederatedRepoNew(ctx context.Context, repository *forgefed.Repository) erro
|
|||
|
||||
if repository.ForkedFrom != nil {
|
||||
repo.IsFork = true
|
||||
forkedFrom, err := repositoryIRIToRepository(ctx, repository.ForkedFrom.GetLink())
|
||||
forkedFrom, err := RepositoryIRIToRepository(ctx, repository.ForkedFrom.GetLink())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
|
@ -15,11 +15,11 @@ import (
|
|||
|
||||
// Process a Like activity to star a repository
|
||||
func ReceiveStar(ctx context.Context, like ap.Like) (err error) {
|
||||
user, err := personIRIToUser(ctx, like.Actor.GetLink())
|
||||
user, err := PersonIRIToUser(ctx, like.Actor.GetLink())
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
repo, err := repositoryIRIToRepository(ctx, like.Object.GetLink())
|
||||
repo, err := RepositoryIRIToRepository(ctx, like.Object.GetLink())
|
||||
if err != nil || strings.Contains(repo.Name, "@") || repo.IsPrivate {
|
||||
return
|
||||
}
|
||||
|
|
|
@ -15,6 +15,7 @@ import (
|
|||
"code.gitea.io/gitea/modules/activitypub"
|
||||
gitea_context "code.gitea.io/gitea/modules/context"
|
||||
"code.gitea.io/gitea/modules/setting"
|
||||
user_service "code.gitea.io/gitea/services/user"
|
||||
|
||||
ap "github.com/go-ap/activitypub"
|
||||
"github.com/go-fed/httpsig"
|
||||
|
@ -84,7 +85,7 @@ func verifyHTTPSignatures(ctx *gitea_context.APIContext) (authenticated bool, er
|
|||
return
|
||||
}
|
||||
|
||||
err = activitypub.FederatedUserNew(ctx, &person)
|
||||
err = user_service.FederatedUserNew(ctx, &person)
|
||||
return authenticated, err
|
||||
}
|
||||
|
||||
|
|
|
@ -13,6 +13,7 @@ import (
|
|||
"code.gitea.io/gitea/modules/convert"
|
||||
api "code.gitea.io/gitea/modules/structs"
|
||||
"code.gitea.io/gitea/routers/api/v1/utils"
|
||||
user_service "code.gitea.io/gitea/services/user"
|
||||
)
|
||||
|
||||
func responseAPIUsers(ctx *context.APIContext, users []*user_model.User) {
|
||||
|
@ -219,7 +220,7 @@ func Follow(ctx *context.APIContext) {
|
|||
// "204":
|
||||
// "$ref": "#/responses/empty"
|
||||
|
||||
if err := user_model.FollowUser(ctx.Doer.ID, ctx.ContextUser.ID); err != nil {
|
||||
if err := user_service.FollowUser(ctx.Doer.ID, ctx.ContextUser.ID); err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "FollowUser", err)
|
||||
return
|
||||
}
|
||||
|
@ -241,7 +242,7 @@ func Unfollow(ctx *context.APIContext) {
|
|||
// "204":
|
||||
// "$ref": "#/responses/empty"
|
||||
|
||||
if err := user_model.UnfollowUser(ctx.Doer.ID, ctx.ContextUser.ID); err != nil {
|
||||
if err := user_service.UnfollowUser(ctx.Doer.ID, ctx.ContextUser.ID); err != nil {
|
||||
ctx.Error(http.StatusInternalServerError, "UnfollowUser", err)
|
||||
return
|
||||
}
|
||||
|
|
|
@ -2,14 +2,16 @@
|
|||
// Use of this source code is governed by a MIT-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
package activitypub
|
||||
package web
|
||||
|
||||
import (
|
||||
"net/http"
|
||||
"net/url"
|
||||
|
||||
"code.gitea.io/gitea/modules/activitypub"
|
||||
"code.gitea.io/gitea/modules/context"
|
||||
"code.gitea.io/gitea/modules/forgefed"
|
||||
user_service "code.gitea.io/gitea/services/user"
|
||||
|
||||
ap "github.com/go-ap/activitypub"
|
||||
)
|
||||
|
@ -20,7 +22,7 @@ func AuthorizeInteraction(ctx *context.Context) {
|
|||
ctx.ServerError("Could not parse URI", err)
|
||||
return
|
||||
}
|
||||
resp, err := Fetch(uri)
|
||||
resp, err := activitypub.Fetch(uri)
|
||||
if err != nil {
|
||||
ctx.ServerError("Fetch", err)
|
||||
return
|
||||
|
@ -40,12 +42,12 @@ func AuthorizeInteraction(ctx *context.Context) {
|
|||
ctx.ServerError("UnmarshalJSON", err)
|
||||
return
|
||||
}
|
||||
err = FederatedUserNew(ctx, object.(*ap.Person))
|
||||
err = user_service.FederatedUserNew(ctx, object.(*ap.Person))
|
||||
if err != nil {
|
||||
ctx.ServerError("FederatedUserNew", err)
|
||||
return
|
||||
}
|
||||
name, err := personIRIToName(object.GetLink())
|
||||
name, err := activitypub.PersonIRIToName(object.GetLink())
|
||||
if err != nil {
|
||||
ctx.ServerError("personIRIToName", err)
|
||||
return
|
||||
|
@ -53,13 +55,13 @@ func AuthorizeInteraction(ctx *context.Context) {
|
|||
ctx.Redirect(name)
|
||||
case forgefed.RepositoryType:
|
||||
err = forgefed.OnRepository(object, func(r *forgefed.Repository) error {
|
||||
return FederatedRepoNew(ctx, r)
|
||||
return activitypub.FederatedRepoNew(ctx, r)
|
||||
})
|
||||
if err != nil {
|
||||
ctx.ServerError("FederatedRepoNew", err)
|
||||
return
|
||||
}
|
||||
username, reponame, err := repositoryIRIToName(object.GetLink())
|
||||
username, reponame, err := activitypub.RepositoryIRIToName(object.GetLink())
|
||||
if err != nil {
|
||||
ctx.ServerError("repositoryIRIToName", err)
|
||||
return
|
||||
|
@ -67,7 +69,7 @@ func AuthorizeInteraction(ctx *context.Context) {
|
|||
ctx.Redirect(username + "/" + reponame)
|
||||
case forgefed.TicketType:
|
||||
err = forgefed.OnTicket(object, func(t *forgefed.Ticket) error {
|
||||
return ReceiveIssue(ctx, t)
|
||||
return activitypub.ReceiveIssue(ctx, t)
|
||||
})
|
||||
if err != nil {
|
||||
ctx.ServerError("ReceiveIssue", err)
|
|
@ -23,6 +23,7 @@ import (
|
|||
"code.gitea.io/gitea/modules/util"
|
||||
"code.gitea.io/gitea/routers/web/feed"
|
||||
"code.gitea.io/gitea/routers/web/org"
|
||||
user_service "code.gitea.io/gitea/services/user"
|
||||
)
|
||||
|
||||
// Profile render user's profile page
|
||||
|
@ -302,9 +303,9 @@ func Action(ctx *context.Context) {
|
|||
var err error
|
||||
switch ctx.FormString("action") {
|
||||
case "follow":
|
||||
err = user_model.FollowUser(ctx.Doer.ID, ctx.ContextUser.ID)
|
||||
err = user_service.FollowUser(ctx.Doer.ID, ctx.ContextUser.ID)
|
||||
case "unfollow":
|
||||
err = user_model.UnfollowUser(ctx.Doer.ID, ctx.ContextUser.ID)
|
||||
err = user_service.UnfollowUser(ctx.Doer.ID, ctx.ContextUser.ID)
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
|
|
|
@ -12,7 +12,6 @@ import (
|
|||
|
||||
"code.gitea.io/gitea/models/perm"
|
||||
"code.gitea.io/gitea/models/unit"
|
||||
"code.gitea.io/gitea/modules/activitypub"
|
||||
"code.gitea.io/gitea/modules/cache"
|
||||
"code.gitea.io/gitea/modules/context"
|
||||
"code.gitea.io/gitea/modules/git"
|
||||
|
@ -1317,7 +1316,7 @@ func RegisterRoutes(m *web.Route) {
|
|||
}, reqSignIn)
|
||||
|
||||
if setting.Federation.Enabled {
|
||||
m.Get("/authorize_interaction", activitypub.AuthorizeInteraction)
|
||||
m.Get("/authorize_interaction", AuthorizeInteraction)
|
||||
}
|
||||
|
||||
if setting.API.EnableSwagger {
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
// Use of this source code is governed by a MIT-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
package activitypub
|
||||
package user
|
||||
|
||||
import (
|
||||
"context"
|
||||
|
@ -11,15 +11,55 @@ import (
|
|||
|
||||
"code.gitea.io/gitea/models/auth"
|
||||
user_model "code.gitea.io/gitea/models/user"
|
||||
"code.gitea.io/gitea/modules/activitypub"
|
||||
"code.gitea.io/gitea/modules/setting"
|
||||
user_service "code.gitea.io/gitea/services/user"
|
||||
|
||||
ap "github.com/go-ap/activitypub"
|
||||
)
|
||||
|
||||
// FollowUser marks someone be another's follower.
|
||||
func FollowUser(userID, followID int64) (err error) {
|
||||
if userID == followID || user_model.IsFollowing(userID, followID) {
|
||||
return nil
|
||||
}
|
||||
|
||||
followUser, err := user_model.GetUserByID(followID)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if followUser.LoginType == auth.Federated {
|
||||
// Following remote user
|
||||
actorUser, err := user_model.GetUserByID(userID)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
object := ap.PersonNew(ap.IRI(followUser.LoginName))
|
||||
follow := ap.FollowNew("", object)
|
||||
follow.Type = ap.FollowType
|
||||
follow.Actor = ap.PersonNew(ap.IRI(setting.AppURL+"api/v1/activitypub/user/"+actorUser.Name))
|
||||
follow.To = ap.ItemCollection{ap.Item(ap.IRI(followUser.LoginName+"/inbox"))}
|
||||
err = activitypub.Send(actorUser, follow)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return user_model.FollowUser(userID, followID)
|
||||
}
|
||||
|
||||
// UnfollowUser unmarks someone as another's follower.
|
||||
func UnfollowUser(userID, followID int64) (err error) {
|
||||
if userID == followID || !user_model.IsFollowing(userID, followID) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return user_model.UnfollowUser(userID, followID)
|
||||
}
|
||||
|
||||
// Create a new federated user from a Person object
|
||||
func FederatedUserNew(ctx context.Context, person *ap.Person) error {
|
||||
name, err := personIRIToName(person.GetLink())
|
||||
name, err := activitypub.PersonIRIToName(person.GetLink())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -63,12 +103,12 @@ func FederatedUserNew(ctx context.Context, person *ap.Person) error {
|
|||
return err
|
||||
}
|
||||
|
||||
body, err := Fetch(iconURL)
|
||||
body, err := activitypub.Fetch(iconURL)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = user_service.UploadAvatar(user, body)
|
||||
err = UploadAvatar(user, body)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
Loading…
Reference in New Issue