Load or create a P2P topic. There is a reace condition when two users try to create a p2p topic at the same time.
(t *Topic, sreg *ClientComMessage)
| 225 | // Load or create a P2P topic. |
| 226 | // There is a reace condition when two users try to create a p2p topic at the same time. |
| 227 | func initTopicP2P(t *Topic, sreg *ClientComMessage) error { |
| 228 | pktsub := sreg.Sub |
| 229 | |
| 230 | // Handle the following cases: |
| 231 | // 1. Neither topic nor subscriptions exist: create a new p2p topic & subscriptions. |
| 232 | // 2. Topic exists, one of the subscriptions is missing: |
| 233 | // 2.1 Requester's subscription is missing, recreate it. |
| 234 | // 2.2 Other user's subscription is missing, treat like a new request for user 2. |
| 235 | // 3. Topic exists, both subscriptions are missing: should not happen, fail. |
| 236 | // 4. Topic and both subscriptions exist: attach to topic |
| 237 | |
| 238 | t.cat = types.TopicCatP2P |
| 239 | |
| 240 | // Check if the topic already exists |
| 241 | stopic, err := store.Topics.Get(t.name) |
| 242 | if err != nil { |
| 243 | return err |
| 244 | } |
| 245 | |
| 246 | // If topic exists, load subscriptions |
| 247 | var subs []types.Subscription |
| 248 | if stopic != nil { |
| 249 | // Subs already have Public swapped |
| 250 | if subs, err = store.Topics.GetUsers(t.name, nil); err != nil { |
| 251 | return err |
| 252 | } |
| 253 | |
| 254 | // Case 3, fail |
| 255 | if len(subs) == 0 { |
| 256 | logs.Err.Println("hub: missing both subscriptions for '" + t.name + "' (SHOULD NEVER HAPPEN!)") |
| 257 | return types.ErrInternal |
| 258 | } |
| 259 | |
| 260 | t.created = stopic.CreatedAt |
| 261 | t.updated = stopic.UpdatedAt |
| 262 | if !stopic.TouchedAt.IsZero() { |
| 263 | t.touched = stopic.TouchedAt |
| 264 | } |
| 265 | t.aux = stopic.Aux |
| 266 | t.lastID = stopic.SeqId |
| 267 | t.delID = stopic.DelId |
| 268 | } |
| 269 | |
| 270 | // t.owner is blank for p2p topics |
| 271 | |
| 272 | // Default user access to P2P topics is not set because it's unused. |
| 273 | // Other users cannot join the topic because of how topic name is constructed. |
| 274 | // The two participants set each other's access instead. |
| 275 | // t.accessAuth = getDefaultAccess(t.cat, true) |
| 276 | // t.accessAnon = getDefaultAccess(t.cat, false) |
| 277 | |
| 278 | // t.public and t.trusted are not used for p2p topics since each user get a different public/trusted. |
| 279 | |
| 280 | if stopic != nil && len(subs) == 2 { |
| 281 | // Case 4. |
| 282 | for i := range 2 { |
| 283 | uid := types.ParseUid(subs[i].User) |
| 284 | t.perUser[uid] = perUserData{ |
no test coverage detected
searching dependent graphs…