b85df0a600a946623bbe3e5b41e1dc6785e2f59c
braney
  Thu Apr 15 17:20:43 2021 -0700
if a track hub specifies a database that's not native, look for in among
the attached hubs, and if it's not there, look on genark

diff --git src/hg/lib/hubConnect.c src/hg/lib/hubConnect.c
index 108a6ef..18505fc 100644
--- src/hg/lib/hubConnect.c
+++ src/hg/lib/hubConnect.c
@@ -185,30 +185,32 @@
     "select hubUrl,status, errorMessage,lastNotOkTime, shortLabel from %s where id=%d", getHubStatusTableName(), id);
 struct sqlResult *sr = sqlGetResult(conn, query);
 char **row = sqlNextRow(sr);
 if (row != NULL)
     {
     AllocVar(hub);
     hub->id = id;
     hub->hubUrl = cloneString(row[0]);
     hub->status = sqlUnsigned(row[1]);
     hub->errorMessage = cloneString(row[2]);
     char *shortLabel = row[4];
     if (isEmpty(row[2]) || hubTimeToCheck(hub, row[3]))
 	{
 	char *errorMessage = NULL;
 	hub->trackHub = fetchHub( hub, &errorMessage);
+        if (hub->trackHub)
+            hub->trackHub->hubStatus = hub;
 	hub->errorMessage = cloneString(errorMessage);
 	hubUpdateStatus( hub->errorMessage, hub);
 	if (!isEmpty(hub->errorMessage))
 	    {
             boolean isCollection = (strstr(hub->hubUrl, "hgComposite") != NULL);
             if (isCollection)
                 warn("You created a <a href=\"/cgi-bin/hgCollection\"><b>Track "
          "Collection</b></a> that has expired and been removed. Track Collections "
          "expire 48 hours after their last use. <a href=\"/cgi-bin/hgSession\"><b>"
          "Save your session</b></a> to preserve collections long-term and to allow sharing.");
             else
                 warn("Could not connect to hub \"%s\": %s", shortLabel, hub->errorMessage);
 	    }
 	}
     }
@@ -858,36 +860,122 @@
 }
 
 struct trackHub *hubConnectGetHubForDb(char *db)
 /* Return the connected hub for db, or NULL if not found.  Do not free result. */
 {
 unsigned hubId = hubIdFromTrackName(db);
 struct hubConnectStatus *status;
 for (status = globalHubList;  status != NULL;  status = status->next)
     {
     if (status->id == hubId)
         return status->trackHub;
     }
 return NULL;
 }
 
+static unsigned lookForUndecoratedDb(char *name)
+// Look for this undecorated in the attached assembly hubs
+{
+struct trackHubGenome *genome = trackHubGetGenomeUndecorated(name);
+
+if (genome == NULL)
+    return FALSE;
+
+struct trackHub *trackHub = genome->trackHub;
+
+if (trackHub != NULL)
+    return trackHub->hubStatus->id;
+return 0;
+}
+
+static boolean lookForLonelyHubs(struct cart *cart, struct hubConnectStatus  *hubList, char **newDatabase, char *genarkPrefix)
+// We go through the hubs and see if any of them reference an assembly
+// that is NOT currently loaded, but we know a URL to load it.
+{
+struct sqlConnection *conn = hConnectCentral();
+boolean added = FALSE;
+
+struct hubConnectStatus  *hub;
+for(hub = hubList; hub; hub = hub->next)
+    {
+    struct trackHub *tHub = hub->trackHub;
+    if (tHub == NULL)
+        continue;
+
+    struct trackHubGenome *genomeList = tHub->genomeList, *genome;
+
+    for(genome = genomeList; genome; genome = genome->next)
+        {
+        char *name = genome->name;
+
+        if (!hDbIsActive(name) )
+            {
+            char buffer[4096];
+            unsigned newId = 0;
+
+            // look with undecorated name for an attached assembly hub
+            if (!(newId = lookForUndecoratedDb(name)))
+                {
+                // see if genark has this assembly
+                char query[4096];
+                sqlSafef(query, sizeof query, "select hubUrl from genark where gcAccession='%s'", name);
+                if (sqlQuickQuery(conn, query, buffer, sizeof buffer))
+                    {
+                    char url[4096];
+                    safef(url, sizeof url, "%s/%s", genarkPrefix, buffer);
+
+                    struct hubConnectStatus *status = getAndSetHubStatus( cart, url, TRUE);
+
+                    if (status)
+                        {
+                        newId = status->id;
+                        added = TRUE;
+                        }
+                    }
+                }
+
+            // if we found an id, change some names to use it as a decoration
+            if (newId)
+                {
+                safef(buffer, sizeof buffer, "hub_%d_%s", newId, name);
+
+                genome->name = cloneString(buffer);
+    
+                // if our new database is an undecorated db, decorate it
+                if (*newDatabase && sameString(*newDatabase, name))
+                    *newDatabase = cloneString(buffer);
+                }
+
+            }
+        }
+    }
+
+hDisconnectCentral(&conn);
+return added;
+}
+
 char *hubConnectLoadHubs(struct cart *cart)
 /* load the track data hubs.  Set a static global to remember them */
 {
 char *newDatabase = checkForNew( cart);
 cartSetString(cart, hgHubConnectRemakeTrackHub, "on");
 struct hubConnectStatus  *hubList =  hubConnectStatusListFromCart(cart);
+
+char *genarkPrefix = cfgOption("genarkHubPrefix");
+if (genarkPrefix && lookForLonelyHubs(cart, hubList, &newDatabase, genarkPrefix))
+    hubList = hubConnectStatusListFromCart(cart);
+
 globalHubList = hubList;
 
 return newDatabase;
 }
 
 char *hubNameFromUrl(char *hubUrl)
 /* Given the URL for a hub, return its hub_# name. */
 {
 char query[PATH_LEN*4];
 sqlSafef(query, sizeof(query), "select concat('hub_', id) from %s where hubUrl = '%s'",
          getHubStatusTableName(), hubUrl);
 struct sqlConnection *conn = hConnectCentral();
 char *name = sqlQuickString(conn, query);
 hDisconnectCentral(&conn);
 return name;