void stopUpload(struct sqlConnection *conn) /* Try and stop current upload. */ { char *url = trimSpaces(cgiString("url")); cgiMakeHiddenVar("url", url); struct edwSubmit *sub = edwMostRecentSubmission(conn, url); if (sub == NULL) { /* Submission hasn't happened yet - remove it from job queue. */ unsigned edwSubmitJobId = 0; int posInQueue = edwSubmitPositionInQueue(conn, url, &edwSubmitJobId); if (posInQueue >= 0) { char query[256]; sqlSafef(query, sizeof(query), "delete from edwSubmitJob where id=%u", edwSubmitJobId); sqlUpdate(conn, query); printf("Removed submission from %s from job queue\n", url); } } else { char query[256]; sqlSafef(query, sizeof(query), "update edwSubmit set errorMessage='Stopped by user.' where id=%u", sub->id); sqlUpdate(conn, query); } monitorSubmission(conn); }
void notOverlappingSelf(struct sqlConnection *conn, char *url) /* Ensure we are only submission going on for this URL, allowing for time out * and command line override. */ { if (doNow) // Allow command line override return; /* Fetch most recent submission from this URL. */ struct edwSubmit *old = edwMostRecentSubmission(conn, url); if (old == NULL) return; /* See if we have something in progress, meaning started but not ended. */ if (old->endUploadTime == 0 && isEmpty(old->errorMessage)) { /* Check submission last alive time against our usual time out. */ long long maxStartTime = edwSubmitMaxStartTime(old, conn); if (edwNow() - maxStartTime < edwSingleFileTimeout) errAbort("Submission of %s already is in progress. Please come back in an hour", url); } edwSubmitFree(&old); }
void edwScriptSubmitStatus() /* edwScriptSubmitStatus - Programatically check status of submission.. */ { /* Pause a second - prevent inadvertent harsh denial of service from scripts. */ sleep(2); edwScriptRegistryFromCgi(); /* Get submission from url. */ struct sqlConnection *conn = edwConnect(); char query[512]; char *url = cgiString("url"); struct edwSubmit *sub = edwMostRecentSubmission(conn, url); char *status = NULL; if (sub == NULL) { int posInQueue = edwSubmitPositionInQueue(conn, url, NULL); if (posInQueue == -1) errAbort("%s has not been submitted", url); else status = "pending"; } else { time_t endUploadTime = sub->endUploadTime; if (!isEmpty(sub->errorMessage)) { status = "error"; } else if (endUploadTime == 0) { status = "uploading"; } else { safef(query, sizeof(query), "select count(*) from edwFile where submitId=%u and errorMessage != ''", sub->id); int errCount = sqlQuickNum(conn, query); int newValid = edwSubmitCountNewValid(sub, conn); if (newValid + errCount < sub->newFiles) status = "validating"; else if (errCount > 0) status = "error"; else status = "success"; } } /* Construct JSON result */ struct dyString *dy = dyStringNew(0); dyStringPrintf(dy, "{\n"); dyStringPrintf(dy, " \"status\": \"%s\"", status); if (sameString(status, "error")) { dyStringPrintf(dy, ",\n"); dyStringPrintf(dy, " \"errors\": [\n"); int errCount = 0; if (!isEmpty(sub->errorMessage)) { addErrFile(dy, errCount, sub->url, sub->errorMessage); ++errCount; } safef(query, sizeof(query), "select * from edwFile where submitId=%u and errorMessage != ''", sub->id); struct edwFile *file, *fileList = edwFileLoadByQuery(conn, query); for (file = fileList; file != NULL; file = file->next) { addErrFile(dy, errCount, file->submitFileName, file->errorMessage); ++errCount; } dyStringPrintf(dy, "\n ]\n"); dyStringPrintf(dy, "}\n"); } else { dyStringPrintf(dy, "\n}\n"); } /* Write out HTTP response */ printf("Content-Length: %d\r\n", dy->stringSize); puts("Content-Type: application/json; charset=UTF-8\r"); puts("\r"); printf("%s", dy->string); }
void monitorSubmission(struct sqlConnection *conn) /* Write out information about submission. */ { char *url = trimSpaces(cgiString("url")); cgiMakeHiddenVar("url", url); struct edwSubmit *sub = edwMostRecentSubmission(conn, url); time_t startTime = 0, endTime = 0, endUploadTime = 0; if (sub == NULL) { int posInQueue = edwSubmitPositionInQueue(conn, url, NULL); if (posInQueue == 0) printf("%s is first in the submission queue, but upload has not started<BR>\n", url); else if (posInQueue > 0) printf("%s is in submission queue with %d submissions ahead of it<BR>\n", url, posInQueue); else { printf("%s status unknown.", url); } } else { startTime = sub->startUploadTime; endUploadTime = sub->endUploadTime; endTime = (endUploadTime ? endUploadTime : edwNow()); int timeSpan = endTime - startTime; long long thisUploadSize = sub->byteCount - sub->oldBytes; long long curSize = 0; // Amount of current file we know we've transferred. /* Print title letting them know if upload is done or in progress. */ printf("<B>Submission by %s is ", userEmail); if (!isEmpty(sub->errorMessage)) { if (endUploadTime == 0) printf("having problems..."); else printf("stopped by uploader request."); } else if (endUploadTime != 0) { printf("uploaded."); } else printf("in progress..."); printf("</B><BR>\n"); /* Print URL and how far along we are at the file level. */ if (!isEmpty(sub->errorMessage)) { printf("<B>error:</B> %s<BR>\n", sub->errorMessage); cgiMakeButton("getUrl", "try submission again"); printf("<BR>"); } printf("<B>url:</B> %s<BR>\n", sub->url); printf("<B>files count:</B> %d<BR>\n", sub->fileCount); if (sub->oldFiles > 0) printf("<B>files already in warehouse:</B> %u<BR>\n", sub->oldFiles); if (sub->metaChangeCount > 0) printf("<B>old files with new tags in this submission</B> %d<BR>", sub->metaChangeCount); if (sub->oldFiles != sub->fileCount) { printf("<B>files transferred:</B> %u<BR>\n", sub->newFiles); printf("<B>files remaining:</B> %u<BR>\n", sub->fileCount - sub->oldFiles - sub->newFiles); } /* Report validation status */ printf("<B>new files validated:</B> %u of %u<BR>\n", edwSubmitCountNewValid(sub, conn), sub->newFiles); /* Print error message, and in case of error skip file-in-transfer info. */ if (isEmpty(sub->errorMessage)) { /* If possible print information about file en route */ if (endUploadTime == 0) { struct edwFile *ef = edwFileInProgress(conn, sub->id); if (ef != NULL) { char path[PATH_LEN]; safef(path, sizeof(path), "%s%s", edwRootDir, ef->edwFileName); if (ef->endUploadTime > 0) curSize = ef->size; else curSize = paraFetchedSoFar(path); printf("<B>file in route:</B> %s", ef->submitFileName); printf(" (%d%% transferred)<BR>\n", (int)(100.0 * curSize / ef->size)); } } } /* Report bytes transferred */ long long transferredThisTime = curSize + sub->newBytes; printf("<B>total bytes transferred:</B> "); long long totalTransferred = transferredThisTime + sub->oldBytes; printLongWithCommas(stdout, totalTransferred); printf(" of "); printLongWithCommas(stdout, sub->byteCount); if (sub->byteCount != 0) printf(" (%d%%)<BR>\n", (int)(100.0 * totalTransferred / sub->byteCount)); else printf("<BR>\n"); /* Report transfer speed if possible */ if (isEmpty(sub->errorMessage)) { if (timeSpan > 0) { printf("<B>transfer speed:</B> "); printLongWithCommas(stdout, (curSize + sub->newBytes)/timeSpan); printf(" bytes/sec<BR>\n"); } /* Report start time and duration */ printf("<B>submission started:</B> %s<BR>\n", ctime(&startTime)); struct dyString *duration = edwFormatDuration(timeSpan); /* Try and give them an ETA if we aren't finished */ if (endUploadTime == 0 && timeSpan > 0) { printf("<B>time so far:</B> %s<BR>\n", duration->string); double bytesPerSecond = (double)transferredThisTime/timeSpan; long long bytesRemaining = thisUploadSize - curSize - sub->newBytes; if (bytesPerSecond > 0) { long long estimatedFinish = bytesRemaining/bytesPerSecond; struct dyString *eta = edwFormatDuration(estimatedFinish); printf("<B>estimated finish in:</B> %s<BR>\n", eta->string); } } else { printf("<B>submission time:</B> %s<BR>\n", duration->string); cgiMakeButton("getUrl", "submit another data set"); } } } cgiMakeButton("monitor", "refresh status"); if (endUploadTime == 0 && isEmpty(sub->errorMessage)) cgiMakeButton(stopButtonName, "stop upload"); printf(" <input type=\"button\" value=\"browse submissions\" " "onclick=\"window.location.href='edwWebBrowse';\">\n"); edwPrintLogOutButton(); }