fetchAndLoadConfigs retrieves all database configs from the ServerContext's bootstrapConnection, and loads them into the ServerContext. It will remove any databases currently running that are not found in the bucket.
(ctx context.Context, isInitialStartup bool)
| 1648 | // fetchAndLoadConfigs retrieves all database configs from the ServerContext's bootstrapConnection, and loads them into the ServerContext. |
| 1649 | // It will remove any databases currently running that are not found in the bucket. |
| 1650 | func (sc *ServerContext) fetchAndLoadConfigs(ctx context.Context, isInitialStartup bool) (count int, err error) { |
| 1651 | fetchedConfigs, err := sc.FetchConfigs(ctx, isInitialStartup) |
| 1652 | if err != nil { |
| 1653 | return 0, err |
| 1654 | } |
| 1655 | |
| 1656 | // Check if we need to update the set of databases before we have to acquire the write lock to do so |
| 1657 | // we don't need to do this two-stage lock on initial startup as the REST APIs aren't even online yet. |
| 1658 | var deletedDatabases []string |
| 1659 | if !isInitialStartup { |
| 1660 | sc._databasesLock.RLock() |
| 1661 | for dbName, _ := range sc._dbRegistry { |
| 1662 | if _, foundMatchingDb := fetchedConfigs[dbName]; !foundMatchingDb { |
| 1663 | deletedDatabases = append(deletedDatabases, dbName) |
| 1664 | delete(fetchedConfigs, dbName) |
| 1665 | } |
| 1666 | } |
| 1667 | for dbName, fetchedConfig := range fetchedConfigs { |
| 1668 | if dbConfig, ok := sc._dbConfigs[dbName]; ok && dbConfig.cfgCas >= fetchedConfig.cfgCas { |
| 1669 | sc.invalidDatabaseConfigTracking.remove(dbName) |
| 1670 | base.DebugfCtx(ctx, base.KeyConfig, "Database %q bucket %q config has not changed since last update", fetchedConfig.Name, *fetchedConfig.Bucket) |
| 1671 | delete(fetchedConfigs, dbName) |
| 1672 | } |
| 1673 | } |
| 1674 | sc._databasesLock.RUnlock() |
| 1675 | |
| 1676 | // nothing to do, we can bail out without needing the write lock |
| 1677 | if len(deletedDatabases) == 0 && len(fetchedConfigs) == 0 { |
| 1678 | base.TracefCtx(ctx, base.KeyConfig, "No persistent config changes to make") |
| 1679 | return 0, nil |
| 1680 | } |
| 1681 | } |
| 1682 | |
| 1683 | // we have databases to update/remove |
| 1684 | sc._databasesLock.Lock() |
| 1685 | defer sc._databasesLock.Unlock() |
| 1686 | for _, dbName := range deletedDatabases { |
| 1687 | dbc, ok := sc._databases[dbName] |
| 1688 | if !ok { |
| 1689 | base.DebugfCtx(ctx, base.KeyConfig, "Database %q already removed from server context after acquiring write lock - do not need to remove not removing database", base.MD(dbName)) |
| 1690 | continue |
| 1691 | } |
| 1692 | // It's possible that the "deleted" database was not written to the server until after sc.FetchConfigs had returned... |
| 1693 | // we'll need to pay for the cost of getting the config again now that we've got the write lock to double-check this db is definitely ok to remove... |
| 1694 | found, _, getConfigErr := sc._fetchDatabaseFromBucket(ctx, dbc.Bucket.GetName(), dbName) |
| 1695 | if found && getConfigErr == nil { |
| 1696 | base.DebugfCtx(ctx, base.KeyConfig, "Found config for database %q after acquiring write lock - not removing database", base.MD(dbName)) |
| 1697 | continue |
| 1698 | } |
| 1699 | if base.IsTemporaryKvError(getConfigErr) { |
| 1700 | base.InfofCtx(ctx, base.KeyConfig, "Transient error fetching config for database %q to check whether we need to remove it, will not be removed: %v", base.MD(dbName), getConfigErr) |
| 1701 | continue |
| 1702 | } |
| 1703 | |
| 1704 | if !found { |
| 1705 | base.InfofCtx(ctx, base.KeyConfig, "Database %q was running on this node, but config was not found on the server - removing database (%v)", base.MD(dbName), getConfigErr) |
| 1706 | sc._removeDatabase(ctx, dbName) |
| 1707 | } |