createOrUpdateNetwork waits for the manifest to be set using manifestOK, then creates or updates the tailnet using the information in the manifest
(manifestOK, networkOK *checkpoint)
| 1466 | // createOrUpdateNetwork waits for the manifest to be set using manifestOK, then creates or updates |
| 1467 | // the tailnet using the information in the manifest |
| 1468 | func (a *agent) createOrUpdateNetwork(manifestOK, networkOK *checkpoint) func(context.Context, proto.DRPCAgentClient28) error { |
| 1469 | return func(ctx context.Context, aAPI proto.DRPCAgentClient28) (retErr error) { |
| 1470 | if err := manifestOK.wait(ctx); err != nil { |
| 1471 | return xerrors.Errorf("no manifest: %w", err) |
| 1472 | } |
| 1473 | defer func() { |
| 1474 | networkOK.complete(retErr) |
| 1475 | }() |
| 1476 | manifest := a.manifest.Load() |
| 1477 | a.closeMutex.Lock() |
| 1478 | network := a.network |
| 1479 | a.closeMutex.Unlock() |
| 1480 | if network == nil { |
| 1481 | keySeed, err := SSHKeySeed(manifest.OwnerName, manifest.WorkspaceName, manifest.AgentName) |
| 1482 | if err != nil { |
| 1483 | return xerrors.Errorf("generate SSH key seed: %w", err) |
| 1484 | } |
| 1485 | // use the graceful context here, because creating the tailnet is not itself tied to the |
| 1486 | // agent API. |
| 1487 | network, err = a.createTailnet( |
| 1488 | a.gracefulCtx, |
| 1489 | manifest.AgentID, |
| 1490 | manifest.DERPMap, |
| 1491 | manifest.DERPForceWebSockets, |
| 1492 | manifest.DisableDirectConnections, |
| 1493 | keySeed, |
| 1494 | ) |
| 1495 | if err != nil { |
| 1496 | return xerrors.Errorf("create tailnet: %w", err) |
| 1497 | } |
| 1498 | a.closeMutex.Lock() |
| 1499 | // Re-check if agent was closed while initializing the network. |
| 1500 | closing := a.closing |
| 1501 | if !closing { |
| 1502 | a.network = network |
| 1503 | a.statsReporter = newStatsReporter(a.logger, network, a) |
| 1504 | } |
| 1505 | a.closeMutex.Unlock() |
| 1506 | if closing { |
| 1507 | _ = network.Close() |
| 1508 | return xerrors.Errorf("agent closed while creating tailnet: %w", ErrAgentClosing) |
| 1509 | } |
| 1510 | } else { |
| 1511 | // Update the wireguard IPs if the agent ID changed. |
| 1512 | err := network.SetAddresses(a.wireguardAddresses(manifest.AgentID)) |
| 1513 | if err != nil { |
| 1514 | a.logger.Error(a.gracefulCtx, "update tailnet addresses", slog.Error(err)) |
| 1515 | } |
| 1516 | // Update the DERP map, force WebSocket setting and allow/disallow |
| 1517 | // direct connections. |
| 1518 | network.SetDERPMap(manifest.DERPMap) |
| 1519 | network.SetDERPForceWebSockets(manifest.DERPForceWebSockets) |
| 1520 | network.SetBlockEndpoints(manifest.DisableDirectConnections) |
| 1521 | |
| 1522 | // Update the subagent client if the container API is available. |
| 1523 | if a.containerAPI != nil { |
| 1524 | client := agentcontainers.NewSubAgentClientFromAPI(a.logger, aAPI) |
| 1525 | a.containerAPI.UpdateSubAgentClient(client) |
no test coverage detected