NCBI C++ ToolKit
netschedule_api_submitter.cpp
Go to the documentation of this file.

Go to the SVN repository for this file.

1 /* $Id: netschedule_api_submitter.cpp 87801 2019-10-04 15:52:36Z sadyrovr $
2  * ===========================================================================
3  *
4  * PUBLIC DOMAIN NOTICE
5  * National Center for Biotechnology Information
6  *
7  * This software/database is a "United States Government Work" under the
8  * terms of the United States Copyright Act. It was written as part of
9  * the author's official duties as a United States Government employee and
10  * thus cannot be copyrighted. This software/database is freely available
11  * to the public for use. The National Library of Medicine and the U.S.
12  * Government have not placed any restriction on its use or reproduction.
13  *
14  * Although all reasonable efforts have been taken to ensure the accuracy
15  * and reliability of the software and data, the NLM and the U.S.
16  * Government do not and cannot warrant the performance or results that
17  * may be obtained by using this software or data. The NLM and the U.S.
18  * Government disclaim all warranties, express or implied, including
19  * warranties of performance, merchantability or fitness for any particular
20  * purpose.
21  *
22  * Please cite the author in any work or product based on this material.
23  *
24  * ===========================================================================
25  *
26  * Author: Anatoliy Kuznetsov, Maxim Didenko, Dmitry Kazimirov
27  *
28  * File Description:
29  * Implementation of NetSchedule API.
30  *
31  */
32 
33 #include <ncbi_pch.hpp>
34 
35 #include "netschedule_api_impl.hpp"
36 
39 
40 #include <stdio.h>
41 #include <cmath>
42 #include <array>
43 
45 
46 using namespace grid::netschedule;
47 
48 #define FORCED_SST_INTERVAL_SEC 0
49 #define MAX_FORCED_SST_INTERVAL_SEC 3
50 #define FORCED_SST_INTERVAL_NANOSEC 500 * 1000 * 1000
51 
52 //////////////////////////////////////////////////////////////////////////////
53 static void s_SerializeJob(string& cmd, const CNetScheduleNewJob& job,
54  unsigned short udp_port, unsigned wait_time)
55 {
56  cmd.push_back('"');
57  cmd.append(NStr::PrintableString(job.input));
58  cmd.push_back('"');
59 
60  if (udp_port && wait_time) {
61  cmd.append(" port=");
62  cmd.append(NStr::UIntToString(udp_port));
63  cmd.append(" timeout=");
64  cmd.append(NStr::UIntToString(wait_time));
65  }
66 
67  if (!job.affinity.empty()) {
68  limits::Check<limits::SAffinity>(job.affinity);
69  cmd.append(" aff=");
70  cmd.append(job.affinity);
71  }
72 
73  if (job.mask != CNetScheduleAPI::eEmptyMask) {
74  cmd.append(" msk=");
75  cmd.append(NStr::UIntToString(job.mask));
76  }
77 }
78 
79 inline
80 void static s_CheckInputSize(const string& input, size_t max_input_size)
81 {
82  if (input.length() > max_input_size) {
83  NCBI_THROW(CNetScheduleException, eDataTooLong,
84  "Input data too long.");
85  }
86 }
87 
89 {
90  return m_Impl->SubmitJobImpl(job, 0, 0);
91 }
92 
93 void SNetScheduleSubmitterImpl::AppendClientIPSessionIDHitID(string& cmd, const string& job_group)
94 {
97 
98  if (!job_group.empty()) {
99  limits::Check<limits::SJobGroup>(job_group);
100  cmd.append(" group=");
101  cmd.append(job_group);
102  }
103 
104  g_AppendHitID(cmd, req);
105 }
106 
108  unsigned short udp_port, unsigned wait_time, CNetServer* server)
109 {
110  size_t max_input_size = m_API->GetServerParams().max_input_size;
111  s_CheckInputSize(job.input, max_input_size);
112 
113  string cmd = "SUBMIT ";
114 
115  s_SerializeJob(cmd, job, udp_port, wait_time);
116  AppendClientIPSessionIDHitID(cmd, job.group);
117 
118  CNetServer::SExecResult exec_result(
119  m_API->m_Service.FindServerAndExec(cmd, false));
120 
121  if ((job.job_id = exec_result.response).empty()) {
122  NCBI_THROW(CNetServiceException, eCommunicationError,
123  "Invalid server response. Empty key.");
124  }
125 
126  if (server != NULL)
127  *server = exec_result.conn->m_Server;
128 
129  return job.job_id;
130 }
131 
132 void CNetScheduleSubmitter::SubmitJobBatch(vector<CNetScheduleJob>& jobs,
133  const string& job_group)
134 {
135  // verify the input data
136  size_t max_input_size = m_Impl->m_API->GetServerParams().max_input_size;
137 
138  ITERATE(vector<CNetScheduleJob>, it, jobs) {
139  const string& input = it->input;
140  s_CheckInputSize(input, max_input_size);
141  }
142 
143  // Batch submit command.
144  string cmd = "BSUB";
145  m_Impl->AppendClientIPSessionIDHitID(cmd, job_group);
146 
147  CNetServer::SExecResult exec_result(
148  m_Impl->m_API->m_Service.FindServerAndExec(cmd, false));
149 
150  cmd.reserve(max_input_size * 6);
151  string host;
152  unsigned short port = 0;
153  for (unsigned i = 0; i < jobs.size(); ) {
154 
155  // Batch size should be reasonable not to trigger network timeout
156  const unsigned kMax_Batch = 10000;
157 
158  size_t batch_size = jobs.size() - i;
159  if (batch_size > kMax_Batch) {
160  batch_size = kMax_Batch;
161  }
162 
163  cmd.erase();
164  cmd = "BTCH ";
165  cmd.append(NStr::UIntToString((unsigned) batch_size));
166 
167  exec_result.conn->WriteLine(cmd);
168 
169  unsigned batch_start = i;
170  for (unsigned j = 0; j < batch_size; ++j,++i) {
171  cmd.erase();
172  s_SerializeJob(cmd, jobs[i], 0, 0);
173 
174  exec_result.conn->WriteLine(cmd);
175  }
176 
177  string resp = exec_result.conn.Exec("ENDB", false);
178 
179  if (resp.empty()) {
180  NCBI_THROW(CNetServiceException, eProtocolError,
181  "Invalid server response. Empty key.");
182  }
183 
184  // parse the batch answer
185  // FORMAT:
186  // first_job_id host port
187 
188  {{
189  const char* s = resp.c_str();
190  unsigned first_job_id = ::atoi(s);
191 
192  if (host.empty()) {
193  for (; *s != ' '; ++s) {
194  if (*s == 0) {
195  NCBI_THROW(CNetServiceException, eProtocolError,
196  "Invalid server response. Batch answer format.");
197  }
198  }
199  ++s;
200  if (*s == 0) {
201  NCBI_THROW(CNetServiceException, eProtocolError,
202  "Invalid server response. Batch answer format.");
203  }
204  for (; *s != ' '; ++s) {
205  if (*s == 0) {
206  NCBI_THROW(CNetServiceException, eProtocolError,
207  "Invalid server response. Batch answer format.");
208  }
209  host.push_back(*s);
210  }
211  ++s;
212  if (*s == 0) {
213  NCBI_THROW(CNetServiceException, eProtocolError,
214  "Invalid server response. Batch answer format.");
215  }
216 
217  port = static_cast<short>(atoi(s));
218  if (port == 0) {
219  NCBI_THROW(CNetServiceException, eProtocolError,
220  "Invalid server response. Port=0.");
221  }
222  }
223 
224  // assign job ids, protocol guarantees all jobs in batch will
225  // receive sequential numbers, so server sends only first job id
226  //
227  CNetScheduleKeyGenerator key_gen(host, port, m_Impl->m_API->m_Queue);
228  for (unsigned j = 0; j < batch_size; ++j) {
229  key_gen.Generate(&jobs[batch_start].job_id, first_job_id);
230  ++first_job_id;
231  ++batch_start;
232  }
233 
234  }}
235 
236 
237  } // for
238 
239  exec_result.conn.Exec("ENDS", false);
240 }
241 
243 {
244 public:
245  CReadCmdExecutor(const string& cmd,
246  string& job_id,
247  string& auth_token,
248  CNetScheduleAPI::EJobStatus& job_status) :
249  m_Cmd(cmd),
250  m_JobId(job_id),
251  m_AuthToken(auth_token),
252  m_JobStatus(job_status)
253  {
254  }
255 
256  virtual bool Consider(CNetServer server);
257 
258 private:
259  string m_Cmd;
260  string& m_JobId;
261  string& m_AuthToken;
263 };
264 
266 {
267  string response = server.ExecWithRetry(m_Cmd, false).response;
268 
269  if (response.empty() || response[0] == '0')
270  return false;
271 
272  m_JobId.erase();
273  m_AuthToken.erase();
274  m_JobStatus = CNetScheduleAPI::eDone;
275 
276  CUrlArgs read_response_parser(response);
277 
278  ITERATE(CUrlArgs::TArgs, it, read_response_parser.GetArgs()) {
279  switch (it->name[0]) {
280  case 'j':
281  if (it->name == "job_key")
282  m_JobId = it->value;
283  break;
284  case 'a':
285  if (it->name == "auth_token")
286  m_AuthToken = it->value;
287  break;
288  case 's':
289  if (it->name == "status")
290  m_JobStatus = CNetScheduleAPI::StringToStatus(it->value);
291  break;
292  }
293  }
294 
295  return !m_JobId.empty();
296 }
297 
298 bool CNetScheduleSubmitter::Read(string* job_id, string* auth_token,
299  CNetScheduleAPI::EJobStatus* job_status, unsigned timeout,
300  const string& job_group)
301 {
302  string cmd("READ ");
303 
304  if (timeout > 0) {
305  cmd += " timeout=";
306  cmd += NStr::UIntToString(timeout);
307  }
308  if (!job_group.empty()) {
309  limits::Check<limits::SJobGroup>(job_group);
310  cmd += " group=";
311  cmd += job_group;
312  }
313 
315 
316  CReadCmdExecutor read_executor(cmd, *job_id, *auth_token, *job_status);
317 
318  return m_Impl->m_API->m_Service.FindServer(&read_executor,
320 }
321 
322 void SNetScheduleSubmitterImpl::FinalizeRead(const char* cmd_start,
323  const string& job_id,
324  const string& auth_token,
325  const string& error_message)
326 {
327  string cmd = cmd_start + job_id;
328 
329  cmd += " auth_token=";
330  cmd += auth_token;
331 
332  if (!error_message.empty()) {
333  cmd += " err_msg=\"";
334  cmd += NStr::PrintableString(error_message);
335  cmd += '"';
336  }
337 
339  m_API->ExecOnJobServer(job_id, cmd, eOn);
340 }
341 
342 void CNetScheduleSubmitter::ReadConfirm(const string& job_id,
343  const string& auth_token)
344 {
345  m_Impl->FinalizeRead("CFRM job_key=",
346  job_id, auth_token, kEmptyStr);
347 }
348 
349 void CNetScheduleSubmitter::ReadRollback(const string& job_id,
350  const string& auth_token)
351 {
352  m_Impl->FinalizeRead("RDRB job_key=",
353  job_id, auth_token, kEmptyStr);
354 }
355 
356 void CNetScheduleSubmitter::ReadFail(const string& job_id,
357  const string& auth_token, const string& error_message)
358 {
359  m_Impl->FinalizeRead("FRED job_key=",
360  job_id, auth_token, error_message);
361 }
362 
365  CNetScheduleJob& job,
366  unsigned wait_time,
367  CNetServer* server)
368 {
369  submitter->SubmitJobImpl(job, GetPort(), wait_time, server);
370 }
371 
373  const string& job_id, CNetScheduleAPI::EJobStatus* job_status,
374  int* last_event_index /*= NULL*/)
375 {
376  _ASSERT(job_status);
377 
378  SNetScheduleOutputParser parser(m_Receiver.message);
379 
380  if (parser("job_key") != job_id) return false;
381 
382  *job_status = CNetScheduleAPI::StringToStatus(parser("job_status"));
383 
384  if (last_event_index) *last_event_index = NStr::StringToInt(parser("last_event_index"), NStr::fConvErr_NoThrow);
385 
386  return *job_status != CNetScheduleAPI::eJobNotFound;
387 }
388 
390  time_t* job_exptime, CNetScheduleAPI::EJobStatus& job_status)
391 {
392  SNetScheduleOutputParser parser(m_Receiver.message);
393 
394  if (parser("job_key") != job.job_id) return false;
395 
396  job_status = CNetScheduleAPI::StringToStatus(parser("job_status"));
397  if (job_status <= CNetScheduleAPI::eRunning) return false;
398 
399  job_status = ns_api.GetJobDetails(job, job_exptime);
400  return job_status > CNetScheduleAPI::eRunning;
401 }
402 
405  unsigned wait_time)
406 {
407  return m_Impl->SubmitJobAndWait(job, wait_time);
408 }
409 
411 SNetScheduleSubmitterImpl::SubmitJobAndWait(CNetScheduleJob& job, unsigned wait_time, time_t* job_exptime)
412 {
413  CDeadline deadline(wait_time, 0);
414 
415  CNetScheduleNotificationHandler submit_job_handler;
416 
417  SubmitJobImpl(job, submit_job_handler.GetPort(), wait_time);
418  if (!wait_time) return CNetScheduleAPI::ePending;
419 
420  return submit_job_handler.WaitForJobCompletion(job, deadline, m_API, job_exptime);
421 }
422 
424 CNetScheduleSubmitter::WaitForJob(const string& job_id, unsigned wait_time)
425 {
426  const CNetScheduleNotificationHandler::TJobStatusMask wait_for_statuses =
430 
431  CDeadline deadline(wait_time);
433  deadline, m_Impl->m_API, wait_for_statuses);
434 }
435 
438  CNetScheduleJob& job,
439  CDeadline& deadline,
440  CNetScheduleAPI ns_api,
441  time_t* job_exptime)
442 {
444 
445  unsigned wait_sec = FORCED_SST_INTERVAL_SEC;
446 
447  for (;;) {
448  CDeadline timeout(wait_sec, FORCED_SST_INTERVAL_NANOSEC);
449 
450  if (deadline < timeout) {
451  timeout = deadline;
452  }
453 
454  if (WaitForNotification(timeout)) {
455  if (GetJobDetailsIfCompleted(ns_api, job, job_exptime, status)) return status;
456  } else {
457  // The wait has timed out - query the server directly.
458 
459  string err_msg;
460  try {
461  status = ns_api.GetJobDetails(job, job_exptime);
462  if ((status != CNetScheduleAPI::eRunning &&
463  status != CNetScheduleAPI::ePending) || deadline.IsExpired())
464  return status;
465  // The job is still running - next time, wait one second
466  // longer before querying the server again.
467  if (wait_sec < MAX_FORCED_SST_INTERVAL_SEC)
468  ++wait_sec;
469  // Go to the next cycle (jump over the error
470  // processing code below the catch blocks).
471  continue;
472  }
473  catch (CNetScheduleException& e) {
474  if (deadline.IsExpired())
475  throw;
476  switch (e.GetErrCode()) {
479  throw;
480  }
481  err_msg = e.GetMsg();
482  }
483  catch (CException& e) {
484  if (deadline.IsExpired())
485  throw;
486  err_msg = e.GetMsg();
487  }
488  // An exception has occurred, but there's still some
489  // time left before the deadline.
490 
491  CNetServer ns_server(ns_api->GetServer(job.job_id));
492  ns_api->GetListener()->OnWarning(err_msg, ns_server);
493 
494  // The notification mechanism may have been disrupted
495  // by the error - query the server more often.
496  wait_sec = FORCED_SST_INTERVAL_SEC;
497  }
498  }
499 }
500 
503  const string& job_id,
504  const CDeadline& deadline,
505  CNetScheduleAPI::EJobStatus* job_status,
506  int* last_event_index)
507 {
508  _ASSERT(job_status);
509  _ASSERT(last_event_index);
510 
511  tie(*job_status, *last_event_index, ignore) = RequestJobWatching(ns_api, job_id, deadline);
512 
513  return *job_status != CNetScheduleAPI::eJobNotFound;
514 }
515 
518  const string& job_id,
519  const CDeadline& deadline)
520 {
521  double remaining_seconds = ceil(deadline.GetRemainingTime().GetAsDouble());
522 
523  string cmd("LISTEN job_key=" + job_id);
524 
525  cmd += " port=";
527  cmd += " timeout=";
528  cmd += NStr::NumericToString((unsigned)remaining_seconds);
529 
531 
532  cmd += " need_progress_msg=1";
533  m_Receiver.message = ns_api->ExecOnJobServer(job_id, cmd, eOn);
534 
535  SNetScheduleOutputParser parser(m_Receiver.message);
536  const auto job_status = CNetScheduleAPI::StringToStatus(parser("job_status"));
537  const auto last_event_index = NStr::StringToInt(parser("last_event_index"), NStr::fConvErr_NoThrow);
538  const auto progress_message = parser("msg");
539 
540  return make_tuple(job_status, last_event_index, progress_message);
541 }
542 
545  const string& job_key,
546  CDeadline& deadline,
547  CNetScheduleAPI ns_api,
548  TJobStatusMask status_mask,
549  int last_event_index,
550  int *new_event_index)
551 {
552  int index = -1;
553 
554  CNetScheduleAPI::EJobStatus job_status;
555 
556  unsigned wait_sec = FORCED_SST_INTERVAL_SEC;
557 
558  do {
559  CDeadline timeout(wait_sec, FORCED_SST_INTERVAL_NANOSEC);
560 
561  if (deadline < timeout) {
562  timeout = deadline;
563  }
564 
565  tie(job_status, index, ignore) = RequestJobWatching(ns_api, job_key, timeout);
566 
567  if ((job_status != CNetScheduleAPI::eJobNotFound) &&
568  ((status_mask & (1 << job_status)) != 0 ||
569  index > last_event_index))
570  break;
571 
572  if (deadline.IsExpired())
573  break;
574 
575  if (!WaitForNotification(timeout))
576  ++wait_sec;
577  else if (CheckJobStatusNotification(job_key, &job_status, &index) &&
578  ((status_mask & (1 << job_status)) != 0 ||
579  index > last_event_index))
580  break;
581  } while (!deadline.IsExpired());
582 
583  if (new_event_index) {
584  *new_event_index = index;
585  }
586 
587  return job_status;
588 }
589 
590 void CNetScheduleSubmitter::CancelJob(const string& job_key)
591 {
592  string cmd("CANCEL " + job_key);
594  m_Impl->m_API->ExecOnJobServer(job_key, cmd);
595 }
596 
597 void CNetScheduleSubmitter::CancelJobGroup(const string& job_group,
598  const string& job_statuses)
599 {
600  limits::Check<limits::SJobGroup>(job_group);
601  string cmd("CANCEL group=" + job_group);
602  if (!job_statuses.empty()) {
603  cmd.append(" status=");
604  cmd.append(job_statuses);
605  }
607  m_Impl->m_API->m_Service.ExecOnAllServers(cmd);
608 }
609 
611  const string& job_key, time_t* job_exptime,
612  ENetScheduleQueuePauseMode* pause_mode)
613 {
614  CNetScheduleJob job;
615  job.job_id = job_key;
616  return m_Impl->m_API->GetJobStatus("SST2", job, job_exptime, pause_mode);
617 }
618 
620  CNetScheduleJob& job, time_t* job_exptime,
621  ENetScheduleQueuePauseMode* pause_mode)
622 {
623  return m_Impl->m_API.GetJobDetails(job, job_exptime, pause_mode);
624 }
625 
627 {
628  m_Impl->m_API.GetProgressMsg(job);
629 }
630 
CDeadline.
Definition: ncbitime.hpp:1830
Client API for NCBI NetSchedule server.
NetSchedule internal exception.
CNetScheduleAPI::EJobStatus WaitForJobEvent(const string &job_key, CDeadline &deadline, CNetScheduleAPI ns_api, TJobStatusMask status_mask, int last_event_index=kMax_Int, int *new_event_index=NULL)
bool CheckJobStatusNotification(const string &job_id, CNetScheduleAPI::EJobStatus *job_status, int *last_event_index=NULL)
tuple< CNetScheduleAPI::EJobStatus, TLastEventIndex, TProgressMessage > TJobInfo
TJobInfo RequestJobWatching(CNetScheduleAPI::TInstance ns_api, const string &job_id, const CDeadline &deadline)
void SubmitJob(CNetScheduleSubmitter::TInstance submitter, CNetScheduleJob &job, unsigned wait_time, CNetServer *server=NULL)
bool GetJobDetailsIfCompleted(CNetScheduleAPI ns_api, CNetScheduleJob &job, time_t *job_exptime, CNetScheduleAPI::EJobStatus &job_status)
CNetScheduleAPI::EJobStatus WaitForJobCompletion(CNetScheduleJob &job, CDeadline &deadline, CNetScheduleAPI ns_api, time_t *job_exptime=NULL)
string Exec(const string &cmd, bool multiline_output=false, const STimeout *timeout=NULL)
Execute remote command 'cmd', wait for the reply, check that it starts with 'OK:',...
SExecResult ExecWithRetry(const string &cmd, bool multiline_output=false)
Execute remote command 'cmd', wait for the reply, check if it starts with 'OK:', and return the remai...
Net Service exception.
virtual bool Consider(CNetServer server)
CReadCmdExecutor(const string &cmd, string &job_id, string &auth_token, CNetScheduleAPI::EJobStatus &job_status)
CNetScheduleAPI::EJobStatus & m_JobStatus
CUrlArgs::
Definition: ncbi_url.hpp:240
static CS_COMMAND * cmd
Definition: ct_dynamic.c:26
#define ITERATE(Type, Var, Cont)
ITERATE macro to sequence through container elements.
Definition: ncbimisc.hpp:815
@ eOn
Definition: ncbi_types.h:111
#define NULL
Definition: ncbistd.hpp:225
static CRequestContext & GetRequestContext(void)
Shortcut to CDiagContextThreadData::GetThreadData().GetRequestContext()
Definition: ncbidiag.cpp:1901
TErrCode GetErrCode(void) const
Get error code.
Definition: ncbiexpt.cpp:453
#define NCBI_THROW(exception_class, err_code, message)
Generic macro to throw an exception, given the exception class, error code and message string.
Definition: ncbiexpt.hpp:704
const string & GetMsg(void) const
Get message string.
Definition: ncbiexpt.cpp:461
EJobStatus
Job status codes.
bool Read(string *job_id, string *auth_token, CNetScheduleAPI::EJobStatus *job_status, unsigned timeout=0, const string &job_group=kEmptyStr)
Incremental retrieval of jobs that are done or failed.
void ReadConfirm(const string &job_id, const string &auth_token)
Mark the specified job as successfully retrieved.
void GetProgressMsg(CNetScheduleJob &job)
Get progress message.
void SubmitJobBatch(vector< CNetScheduleJob > &jobs, const string &job_group=kEmptyStr)
Submit job batch.
EJobStatus GetJobDetails(CNetScheduleJob &job, time_t *job_exptime=NULL, ENetScheduleQueuePauseMode *pause_mode=NULL)
Get job details.
CNetScheduleAPI::EJobStatus SubmitJobAndWait(CNetScheduleJob &job, unsigned wait_time)
Submit job to server and wait for the result.
CNetScheduleAPI::TJobMask mask
CNetScheduleAPI::EJobStatus WaitForJob(const string &job_id, unsigned wait_time)
Wait for job to finish its execution (done/failed/canceled).
string Generate(unsigned id) const
string input
Input data.
CNetScheduleAPI::EJobStatus GetJobDetails(CNetScheduleJob &job, time_t *job_exptime=NULL, ENetScheduleQueuePauseMode *pause_mode=NULL)
Get full information about the specified job.
CNetScheduleAPI::EJobStatus GetJobStatus(const string &job_key, time_t *job_exptime=NULL, ENetScheduleQueuePauseMode *pause_mode=NULL)
Get the current status of the specified job.
void CancelJobGroup(const string &job_group, const string &job_statuses=kEmptyStr)
Cancel job group.
void ReadRollback(const string &job_id, const string &auth_token)
Refuse from processing the results of the specified job.
void ReadFail(const string &job_id, const string &auth_token, const string &error_message=kEmptyStr)
Refuse from processing the results of the specified job and increase its counter of failed job result...
static EJobStatus StringToStatus(const CTempString &status_str)
Parse status string into enumerator value.
string SubmitJob(CNetScheduleNewJob &job)
Submit job.
string job_id
Output job key.
void CancelJob(const string &job_key)
Cancel job.
@ eDone
Job is ready (computed successfully)
@ eRunning
Running on a worker node.
@ eJobNotFound
No such job.
@ ePending
Waiting for execution.
#define END_NCBI_SCOPE
End previously defined NCBI scope.
Definition: ncbistl.hpp:103
#define BEGIN_NCBI_SCOPE
Define ncbi namespace.
Definition: ncbistl.hpp:100
static string PrintableString(const CTempString str, TPrintableMode mode=fNewLine_Quote|fNonAscii_Passthru)
Get a printable version of the specified string.
Definition: ncbistr.cpp:3944
#define kEmptyStr
Definition: ncbistr.hpp:123
static int StringToInt(const CTempString str, TStringToNumFlags flags=0, int base=10)
Convert string to int.
Definition: ncbistr.cpp:630
static string UIntToString(unsigned int value, TNumToStringFlags flags=0, int base=10)
Convert UInt to string.
Definition: ncbistr.hpp:5111
static enable_if< is_arithmetic< TNumeric >::value||is_convertible< TNumeric, Int8 >::value, string >::type NumericToString(TNumeric value, TNumToStringFlags flags=0, int base=10)
Convert numeric value to string.
Definition: ncbistr.hpp:673
@ fConvErr_NoThrow
Do not throw an exception on error.
Definition: ncbistr.hpp:285
unsigned short GetPort() const
Get the listening port number back.
CNanoTimeout GetRemainingTime(void) const
Get time left to the expiration.
Definition: ncbitime.cpp:3859
bool IsExpired(void) const
Check if the deadline is expired.
Definition: ncbitime.hpp:1855
double GetAsDouble(void) const
Get as number of seconds (fractional value).
Definition: ncbitime.cpp:3512
const TArgs & GetArgs(void) const
Get the const list of arguments.
Definition: ncbi_url.hpp:300
list< TArg > TArgs
Definition: ncbi_url.hpp:276
static int input()
int i
NetSchedule client specs.
ENetScheduleQueuePauseMode
Defines whether the job queue is paused, and if so, defines the pause mode set by the administrator.
static void s_SerializeJob(string &cmd, const CNetScheduleNewJob &job, unsigned short udp_port, unsigned wait_time)
#define MAX_FORCED_SST_INTERVAL_SEC
static void s_CheckInputSize(const string &input, size_t max_input_size)
#define FORCED_SST_INTERVAL_SEC
#define FORCED_SST_INTERVAL_NANOSEC
void g_AppendClientIPSessionIDHitID(string &cmd)
void g_AppendClientIPAndSessionID(string &cmd, const CRequestContext &req)
void g_AppendHitID(string &cmd, CRequestContext &req)
Job description.
New job description.
CNetServerConnection conn
void OnWarning(const string &warn_msg, CNetServer &server)
CNetScheduleServerListener * GetListener()
string ExecOnJobServer(const TJob &job, const string &cmd, ESwitch roe=eDefault)
CNetServer GetServer(const string &job_key)
CNetScheduleAPI::EJobStatus SubmitJobAndWait(CNetScheduleJob &job, unsigned wait_time, time_t *job_exptime=NULL)
string SubmitJobImpl(CNetScheduleNewJob &job, unsigned short udp_port, unsigned wait_time, CNetServer *server=NULL)
void AppendClientIPSessionIDHitID(string &cmd, const string &job_group)
void FinalizeRead(const char *cmd_start, const string &job_id, const string &auth_token, const string &error_message)
void WriteLine(const string &line)
#define _ASSERT
Modified on Mon Jul 22 05:05:03 2024 by modify_doxy.py rev. 669887