Async Process Calls - asynchronous

What is the preferred way of calling other processes asynchronously in D? My use case is calling svn status checking exit status, and parsing its standard output and error.

I think std.stdio.popen is what you want:
void popen(string command, in char[] stdioOpenmode = "r");
Use it with a File and you get the output; something like:
File f;
f.popen("svn status", "r");
char[] line;
string result;
while (f.readln(line))
result ~= line;
return result;
Or you can use std.process.shell which apparently does this for you (and throws an ErrnoException on error).

Related

QuickFixJ session config is null. The SessionSettings InputStream InputStreamReader TokenizerToken produces null

In QuickFixJ the config file is not read, causing session settings to be null, but the initiator still starts, but doesn't connect anywhere. There are no log or store directories produced and no error given.
Using the normal config file loading process set out in the docs, the config file is read under the hood by the SessionSettings.java class. It uses the following code:
private void load(InputStream inputStream) throws ConfigError {
try {
Properties currentSection = null;
String currentSectionId = null;
final Tokenizer tokenizer = new Tokenizer();
final Reader reader = new InputStreamReader(inputStream);
Tokenizer.Token token = tokenizer.getToken(reader);
while (token != null) {
...
This is my inputStream
It looks like a good inputStream but the tokenizer is consistently producing null.
There's nothing wrong with the QuickFix config file FIX.cfg that I can see. I am using JDK11.
The issue was that my config file was saved with Character Encoding UTF-8 with BOM by Notepad which was very unexpected.

asp.net Web API most efficient way to replace a request response body to have a consistant error structure

I am using as Web API what uses AuthorisationManager owin middleware to handle token based security.
My problem is that various errors within the response body have various different formats.
Within my api, I usually send errors back with the structure
{"code": "error code", "message": "error message"}
However some of the errors coming from the security may use
{"error": "error code", "error_description": "error message"}
or sometimes just
{"error": "error mesage"}
I would like to unify these to all have the same structure I use elsewhere, ie the
{"code": "error code", "message": "error message"}
I have seen quite a few posts on replacing a response body.
I first tried this method, ie using the DelegatingHandler. This worked in most cases, but it did not catch my authorization failed error messages comding out of my OAuthAuthorizationServerProvider
I next tried using a middleware approach as shown here.
Here is my full interpretation..
public override async Task Invoke(IOwinContext context)
{
try
{
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream())
{
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await this.Next.Invoke(context);
// Error codes start at 400. If we have no errors, no more to d0.
if (context.Response.StatusCode < 400) // <---- *** COMMENT1 ***
return;
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
// If no response body, nothing to do
if (string.IsNullOrEmpty(responseBody))
return;
// If we have the correct error fields names, no more to do
JObject responseBodyJson = JObject.Parse(responseBody);
if (responseBodyJson.ContainsKey("code") && responseBodyJson.ContainsKey("message"))
return;
// Now we will look for the known error formats that we want to replace...
byte[] byteArray = null;
// The first one from the security module, errors come back as {error, error_description}.
// The contents are what we set (so are correct), we just want the fields names to be the standard {code, message}
var securityErrorDescription = responseBodyJson.GetValue("error_description");
var securityErrorCode = responseBodyJson.GetValue("error");
if (securityErrorDescription != null && securityErrorCode != null)
byteArray = CreateErrorObject(securityErrorCode.ToString(), securityErrorDescription.ToString());
// The next horrible format, is when a refresh token is just sends back an object with 'error'.
var refreshTokenError = responseBodyJson.GetValue("error");
if (refreshTokenError != null)
{
// We will give this our own error code
var error = m_resourceProvider.GetRefreshTokenAuthorisationError(refreshTokenError.ToString());
byteArray = CreateErrorObject(error.Item2, error.Item3);
}
else
{
byteArray = Encoding.ASCII.GetBytes(responseBody);
}
// Now replace the response (body) with our now contents
// <---- *** COMMENT2 ***
context.Response.ContentType = "application / json";
context.Response.ContentLength = byteArray.Length;
buffer.SetLength(0);
buffer.Write(byteArray, 0, byteArray.Length);
buffer.Seek(0, SeekOrigin.Begin);
buffer.CopyTo(stream);
}
}
catch (Exception ex)
{
m_logger.WriteError($"ResponseFormattingMiddleware {ex}");
context.Response.StatusCode = 500;
throw;
}
}
private byte[] CreateErrorObject(string code, string message)
{
JObject newMessage = new JObject();
newMessage["code"] = code;
newMessage["message"] = message;
return Encoding.ASCII.GetBytes(newMessage.ToString());
}
So this basically seemed to work, and catch ALL responses, which is good.
However, what I was hoping to do, is, when there is no error, (or the error is already in the correct format), just pass the response on without doing anything with it.
I am mainly thinking of some of my GETs, where the data may be large, I was hoping to avoid having to do the extra copying back. In the above code, where I have marked *** COMMENT1 ***, I have an early return to try to avoid this, ie the line...
// Error codes start at 400. If we have no errors, no more to d0.
if (context.Response.StatusCode < 400)
return;
The problem, is when I do this, I get no body at all returned, ie no data for all the GET calls, etc.
Is there a way to avoid this extra copying (ie at the line *** COMMENT2 ***) when we don't want to do any modifications?
Thanks in advance for any suggestions.
Adding an answer since it has a code snippet but this is really just a comment.
Our services use the delegatingHandler approach you mentioned you tried first. Do you have try/catch around the call to base.SendAsync. In this snippet the requestState is just a wrapper around the incoming request with some timers, loggers, etc. In many cases we replace the response as you are trying. I stepped through the exception and used the VS debugger immediate window to modify the error response. It works for me.(TM)
try
{
return base
.SendAsync(request, cancellationToken)
.ContinueWith(
(task, requestState) => ((InstrumentedRequest)requestState).End(task),
instrumentedRequest,
CancellationToken.None,
TaskContinuationOptions.ExecuteSynchronously,
TaskScheduler.Default)
.Unwrap();
}
catch (Exception ex)
{
instrumentedRequest.PrematureFault(ex);
throw;
}

Task async and await

I want the method PrintOrderAsync to execute an external EXE to print an order.
The code for method PrintOrderAsync does not show any syntax errors
public async Task<string> PrintOrderAsync(string PrintExe, string ExePath, int nOrderNo)
{
await Task.Factory.StartNew(() => Process.Start(ExePath + PrintExe, nOrderNo.ToString()));
return "";
}
But I am struggling with the syntax for the calling method. Here is what I tried:
Task<string> result = PrintOrderAsync(PrintExe, ExePath, nOrderNo);
And I see syntax error on the above line. What am I missing?
Based on the code that you have shared here you are starting a process. This is concerning as you are not actually waiting for the result of the process, in fact -- it is fire and forget regardless of the async and await keywords unless you wait for the process to exit. There are several ways to do this:
public static Task WaitForExitAsync(this Process process,
int milliseconds,
CancellationToken cancellationToken = default(CancellationToken))
{
return Task.Run(() => process.WaitForExit(milliseconds), cancellationToken);
}
For example, here is an extension method you could use to wrap the waiting for the process in a Task. It could then be awaited like this:
public async Task PrintOrderAsync(string PrintExe, string ExePath, int nOrderNo)
{
return Process.Start(ExePath + PrintExe, nOrderNo.ToString())
.WaitForExitAsync(5000);
}
// Then you could await it wherever...
await PrintOrderAsync(PrintExe, ExePath, nOrderNo);
Alternatively, if you do not want to wait for it to complete (i.e.; you want fire and forget, like you have now) do this:
Process.Start(ExePath + PrintExe, nOrderNo.ToString())
Do not wrap it in a Task or anything, it is an entirely separate process anyways (personally, I prefer the first option I shared).
Try
string result = await PrintOrderAsync(PrintExe, ExePath, nOrderNo);

How to lazily stream using HttpServletRequest#getPart(name)

I'm using Jetty 9's implementation of HttpServletRequest#getPart(name), and it appears to eagerly processes the entire request (or at least the Part in question) before continuing, even though the resulting Part exposes a getInputStream() method.
Is there a way for getPart to return immediately, and leave request streaming to the resulting Part's InputStream?
For reference, here's the relevant snippet from my Servlet implementation:
override def doPost(req: HttpServletRequest, res: HttpServletResponse) {
println("ABOUT TO GET PART") // this happens immediately
val file = req.getPart("file")
println("GOT PART") // it takes a long time to get here if the upload is large
It's wicked tedious, but this can be done using MultipartStream from commons-fileupload:
try {
MultipartStream multipartStream = new MultipartStream(input, boundary);
boolean nextPart = multipartStream.skipPreamble();
OutputStream output;
while(nextPart) {
String header = multipartStream.readHeaders();
// process headers
// create some output stream
multipartStream.readBodyData(output);
nextPart = multipartStream.readBoundary();
}
} catch(MultipartStream.MalformedStreamException e) {
// the stream failed to follow required syntax
} catch(IOException e) {
// a read or write error occurred
}
This requires the use of the InputStream from HttpServletRequest#getInputStream(), and the boundary delimiter encoded in the HTTP request's content type:
Content-Type: multipart/form-data; boundary=------------------------bd019839518ca918

sqlite jdbc setJournalMode

I running my first trials on SQLite (with JDBC) as pure memory database. As I need very fast inserts I tried to set the config accordingly. I could find out that the code below fails only at the setting for JournalMode. Please refer to the method shown below. The variables con and isConnected are defined as class vars and not shown here.
Thanks a lot
Rolf
public Boolean connect() {
try {
Class.forName("org.sqlite.JDBC"); // sqlitejdbc_3.7.2
// Set all pragmas
SQLiteConfig config = new SQLiteConfig();
// This statement (JournalMode setting) causes a fail
// Without that statement the connection can be established
// ==> java.sql.BatchUpdateException: batch entry 0: query returns results
config.setJournalMode(JournalMode.MEMORY);
config.setTempStore(TempStore.MEMORY);
config.setSynchronous(SynchronousMode.OFF);
config.enforceForeignKeys(false);
config.enableCountChanges(false);
con = DriverManager.getConnection("jdbc:sqlite::memory:", config.toProperties());
isConnected = true ;
return true ;
}
catch (Exception e) {
LogMessages.instance().print(0, LogMessages.MSG_SEVERITY.ERROR, e.getMessage() + "\n");
e.printStackTrace() ;
return false ;
}
}
I have the same issue, but there is an other way to disable it. After opening the connection you can execute this query :
PRAGMA journal_mode=MEMORY;

Resources