export.go (8353B)
1 // GoToSocial 2 // Copyright (C) GoToSocial Authors admin@gotosocial.org 3 // SPDX-License-Identifier: AGPL-3.0-or-later 4 // 5 // This program is free software: you can redistribute it and/or modify 6 // it under the terms of the GNU Affero General Public License as published by 7 // the Free Software Foundation, either version 3 of the License, or 8 // (at your option) any later version. 9 // 10 // This program is distributed in the hope that it will be useful, 11 // but WITHOUT ANY WARRANTY; without even the implied warranty of 12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 // GNU Affero General Public License for more details. 14 // 15 // You should have received a copy of the GNU Affero General Public License 16 // along with this program. If not, see <http://www.gnu.org/licenses/>. 17 package trans 18 19 import ( 20 "context" 21 "fmt" 22 "os" 23 24 "github.com/superseriousbusiness/gotosocial/internal/db" 25 transmodel "github.com/superseriousbusiness/gotosocial/internal/trans/model" 26 ) 27 28 func (e *exporter) exportAccounts(ctx context.Context, where []db.Where, file *os.File) ([]*transmodel.Account, error) { 29 // select using the 'where' we've been provided 30 accounts := []*transmodel.Account{} 31 if err := e.db.GetWhere(ctx, where, &accounts); err != nil { 32 return nil, fmt.Errorf("exportAccounts: error selecting accounts: %s", err) 33 } 34 35 // write any accounts found to file 36 for _, a := range accounts { 37 if err := e.accountEncode(ctx, file, a); err != nil { 38 return nil, fmt.Errorf("exportAccounts: error encoding account: %s", err) 39 } 40 } 41 42 return accounts, nil 43 } 44 45 func (e *exporter) exportBlocks(ctx context.Context, accounts []*transmodel.Account, file *os.File) ([]*transmodel.Block, error) { 46 blocksUnique := make(map[string]*transmodel.Block) 47 48 // for each account we want to export both where it's blocking and where it's blocked 49 for _, a := range accounts { 50 // 1. export blocks owned by given account 51 whereBlocking := []db.Where{{Key: "account_id", Value: a.ID}} 52 blocking := []*transmodel.Block{} 53 if err := e.db.GetWhere(ctx, whereBlocking, &blocking); err != nil { 54 return nil, fmt.Errorf("exportBlocks: error selecting blocks owned by account %s: %s", a.ID, err) 55 } 56 for _, b := range blocking { 57 b.Type = transmodel.TransBlock 58 if err := e.simpleEncode(ctx, file, b, b.ID); err != nil { 59 return nil, fmt.Errorf("exportBlocks: error encoding block owned by account %s: %s", a.ID, err) 60 } 61 blocksUnique[b.ID] = b 62 } 63 64 // 2. export blocks that target given account 65 whereBlocked := []db.Where{{Key: "target_account_id", Value: a.ID}} 66 blocked := []*transmodel.Block{} 67 if err := e.db.GetWhere(ctx, whereBlocked, &blocked); err != nil { 68 return nil, fmt.Errorf("exportBlocks: error selecting blocks targeting account %s: %s", a.ID, err) 69 } 70 for _, b := range blocked { 71 b.Type = transmodel.TransBlock 72 if err := e.simpleEncode(ctx, file, b, b.ID); err != nil { 73 return nil, fmt.Errorf("exportBlocks: error encoding block targeting account %s: %s", a.ID, err) 74 } 75 blocksUnique[b.ID] = b 76 } 77 } 78 79 // now return all the blocks we found 80 blocks := []*transmodel.Block{} 81 for _, b := range blocksUnique { 82 blocks = append(blocks, b) 83 } 84 85 return blocks, nil 86 } 87 88 func (e *exporter) exportDomainBlocks(ctx context.Context, file *os.File) ([]*transmodel.DomainBlock, error) { 89 domainBlocks := []*transmodel.DomainBlock{} 90 91 if err := e.db.GetAll(ctx, &domainBlocks); err != nil { 92 return nil, fmt.Errorf("exportBlocks: error selecting domain blocks: %s", err) 93 } 94 95 for _, b := range domainBlocks { 96 b.Type = transmodel.TransDomainBlock 97 if err := e.simpleEncode(ctx, file, b, b.ID); err != nil { 98 return nil, fmt.Errorf("exportBlocks: error encoding domain block: %s", err) 99 } 100 } 101 102 return domainBlocks, nil 103 } 104 105 func (e *exporter) exportFollows(ctx context.Context, accounts []*transmodel.Account, file *os.File) ([]*transmodel.Follow, error) { 106 followsUnique := make(map[string]*transmodel.Follow) 107 108 // for each account we want to export both where it's following and where it's followed 109 for _, a := range accounts { 110 // 1. export follows owned by given account 111 whereFollowing := []db.Where{{Key: "account_id", Value: a.ID}} 112 following := []*transmodel.Follow{} 113 if err := e.db.GetWhere(ctx, whereFollowing, &following); err != nil { 114 return nil, fmt.Errorf("exportFollows: error selecting follows owned by account %s: %s", a.ID, err) 115 } 116 for _, follow := range following { 117 follow.Type = transmodel.TransFollow 118 if err := e.simpleEncode(ctx, file, follow, follow.ID); err != nil { 119 return nil, fmt.Errorf("exportFollows: error encoding follow owned by account %s: %s", a.ID, err) 120 } 121 followsUnique[follow.ID] = follow 122 } 123 124 // 2. export follows that target given account 125 whereFollowed := []db.Where{{Key: "target_account_id", Value: a.ID}} 126 followed := []*transmodel.Follow{} 127 if err := e.db.GetWhere(ctx, whereFollowed, &followed); err != nil { 128 return nil, fmt.Errorf("exportFollows: error selecting follows targeting account %s: %s", a.ID, err) 129 } 130 for _, follow := range followed { 131 follow.Type = transmodel.TransFollow 132 if err := e.simpleEncode(ctx, file, follow, follow.ID); err != nil { 133 return nil, fmt.Errorf("exportFollows: error encoding follow targeting account %s: %s", a.ID, err) 134 } 135 followsUnique[follow.ID] = follow 136 } 137 } 138 139 // now return all the follows we found 140 follows := []*transmodel.Follow{} 141 for _, follow := range followsUnique { 142 follows = append(follows, follow) 143 } 144 145 return follows, nil 146 } 147 148 func (e *exporter) exportFollowRequests(ctx context.Context, accounts []*transmodel.Account, file *os.File) ([]*transmodel.FollowRequest, error) { 149 frsUnique := make(map[string]*transmodel.FollowRequest) 150 151 // for each account we want to export both where it's following and where it's followed 152 for _, a := range accounts { 153 // 1. export follow requests owned by given account 154 whereRequesting := []db.Where{{Key: "account_id", Value: a.ID}} 155 requesting := []*transmodel.FollowRequest{} 156 if err := e.db.GetWhere(ctx, whereRequesting, &requesting); err != nil { 157 return nil, fmt.Errorf("exportFollowRequests: error selecting follow requests owned by account %s: %s", a.ID, err) 158 } 159 for _, fr := range requesting { 160 fr.Type = transmodel.TransFollowRequest 161 if err := e.simpleEncode(ctx, file, fr, fr.ID); err != nil { 162 return nil, fmt.Errorf("exportFollowRequests: error encoding follow request owned by account %s: %s", a.ID, err) 163 } 164 frsUnique[fr.ID] = fr 165 } 166 167 // 2. export follow requests that target given account 168 whereRequested := []db.Where{{Key: "target_account_id", Value: a.ID}} 169 requested := []*transmodel.FollowRequest{} 170 if err := e.db.GetWhere(ctx, whereRequested, &requested); err != nil { 171 return nil, fmt.Errorf("exportFollowRequests: error selecting follow requests targeting account %s: %s", a.ID, err) 172 } 173 for _, fr := range requested { 174 fr.Type = transmodel.TransFollowRequest 175 if err := e.simpleEncode(ctx, file, fr, fr.ID); err != nil { 176 return nil, fmt.Errorf("exportFollowRequests: error encoding follow request targeting account %s: %s", a.ID, err) 177 } 178 frsUnique[fr.ID] = fr 179 } 180 } 181 182 // now return all the followRequests we found 183 followRequests := []*transmodel.FollowRequest{} 184 for _, fr := range frsUnique { 185 followRequests = append(followRequests, fr) 186 } 187 188 return followRequests, nil 189 } 190 191 func (e *exporter) exportInstances(ctx context.Context, file *os.File) ([]*transmodel.Instance, error) { 192 instances := []*transmodel.Instance{} 193 194 if err := e.db.GetAll(ctx, &instances); err != nil { 195 return nil, fmt.Errorf("exportInstances: error selecting instance: %s", err) 196 } 197 198 for _, u := range instances { 199 u.Type = transmodel.TransInstance 200 if err := e.simpleEncode(ctx, file, u, u.ID); err != nil { 201 return nil, fmt.Errorf("exportInstances: error encoding instance: %s", err) 202 } 203 } 204 205 return instances, nil 206 } 207 208 func (e *exporter) exportUsers(ctx context.Context, file *os.File) ([]*transmodel.User, error) { 209 users := []*transmodel.User{} 210 211 if err := e.db.GetAll(ctx, &users); err != nil { 212 return nil, fmt.Errorf("exportUsers: error selecting users: %s", err) 213 } 214 215 for _, u := range users { 216 u.Type = transmodel.TransUser 217 if err := e.simpleEncode(ctx, file, u, u.ID); err != nil { 218 return nil, fmt.Errorf("exportUsers: error encoding user: %s", err) 219 } 220 } 221 222 return users, nil 223 }