I want to wrap the upload part in a common function since it is used in multiple API routes, but how do I do it since it is using async def here.
#app.post("/api/od")
async def image_classification(files: typing.List[fastapi.UploadFile] = fastapi.File(...)):
upload_path = pathlib.Path("upload")#.joinpath(token)
upload_path.mkdir(exist_ok=True)
...
return results
Related
I am working on creating a asyncio.Future callback for requests whereby I store the body of the response in json format and return this result. I initially wanted to create a callback on the function on_response, however I was not certain how to implement this. Therefore, I decided to include option parameters to add into the callable such as url.
For example:
import asyncio
from functools import partial as func
import requests
import json
url = "https://www.scrapethissite.com/pages/ajax-javascript/?ajax=true&year=2015"
class schedulerLoop(asyncio.Future):
def __init__(self, url):
super(schedulerLoop, self).__init__()
self._url = url
#staticmethod
def unwrapper(funct):
return funct()
def _future(self, *args):
return self.add_done_callback(func(self.unwrapper, *args))
async def on_response(self):
if self.done():
obj = await self._future(func(requests.get, self._url))
body = json.loads(obj)
return body
else:
self.exception()
async def main(loop):
await loop.on_response()
loop = schedulerLoop(url)
if __name__ == '__main__':
asyncio.run(main(loop))
I find that I get:
asyncio.exceptions.InvalidStateError: Exception is not set.
Which supposes that on_response the Future is not done, and so we get a False result but there seems be no no Exception neither.
In this code snippet, data gets retrieved from Firestore:
val docRef = db.collection("cities").document("BJ")
docRef.get().addOnSuccessListener { documentSnapshot ->
val city = documentSnapshot.toObject<City>()
}
How could I turn this into a function, that returns a city object? Something like this:
fun getCity(): City?{
val docRef = db.collection("cities").document("BJ")
docRef.get().addOnSuccessListener { documentSnapshot ->
val city = documentSnapshot.toObject<City>()
return city
}
Can I somehow 'await' the result when I call the getCity() function?
There's one important thing you'll need to know:
All Firestore APIs are asynchronous. They return immediately, and you must use the callback to get the results. There is no guarantee when the callback will be invoked, and it must be handled asynchronously. Your getCity() function will not be able to return an object immediately.
get() returns a Task object (provided by the Play services Task API) that represents the asynchronous query. If you want to await() the result of that, your easiest route is to use the kotlinx-coroutines-play-services library to convert that task into a suspend fun that can be awaited. If you do this, your getCity() should also be a suspend fun so that it can deliver the result asynchronously to its caller.
See also: How to use kotlin coroutines in firebase database
I have this function, want to call it synchronously, because if I call it async then I should use FutureBuilder, which I don't prefer because it has extra flicker if user scrolls too fast:
Future<String> getRealHTML(int chapter) async {
var key = _Html.keys.toList()[chapter];
var val = _Html.values.toList()[chapter];
if (val.Content.startsWith("filename:")) {
EpubContentFileRef value = contentRefHtml[key];
return await value.readContentAsText();
}
return null;
}
readContentAsText() returns a Future, you cannot call it synchronously since it is an I/O request which means it will take time to finish the request, that is why it is called asychronously.
All my repository methods are async for my CRUD operations using EF.Core async methods and use AutoMapper to map my EF entity model (Customer) to Domain Model (CustomerModel) and pass it back to my service layer.
public async Task<CustomerModel> GetCustomerByIdAsync(int id)
{
Customer customer = await _context.Customers.FindAsync(id);
var mappedResult = _mapper.Map<CustomerModel>(customer);
return await Task.FromResult(mappedResult);
}
Since "_mapper.Map" is not async but GetCustomerByIdAsync is, I return await Task.FromResult(mappedResult) instead of return mappedResult;
My caller method in service layer is also async. Have I got this right? I am also wondering about deadlock implications, although I am not calling any of my async methods from sync methods using .Result.
Thanks for your time.
Since "_mapper.Map" is not async but GetCustomerByIdAsync is, I return await Task.FromResult(mappedResult) instead of return mappedResult;
No, await Task.FromResult(x) doesn't ever make any sense. I've seen this code a lot, and I'm not sure where it comes from.
await Task.FromResult(x) is literally a less-efficient way of writing x. It's less efficient and less maintainable, so I have no idea where this idea came from.
Your code should look like:
public async Task<CustomerModel> GetCustomerByIdAsync(int id)
{
Customer customer = await _context.Customers.FindAsync(id);
var mappedResult = _mapper.Map<CustomerModel>(customer);
return mappedResult;
}
Actually in Dart, in order to use await in function body, one need to declare whole function as async:
import "dart:async";
void main() async {
var x = await funcTwo();
print(x);
}
funcTwo() async {
return 42;
}
This code wouldn't work without marking main() as async
Error: Unexpected token 'await'.
But, doc says "The await expressions evaluates e, and then suspends the currently running function until the result is ready–that is, until the Future has completed" (Dart Language Asynchrony Support)
So, maybe I miss something, but there is no need to force function to be asynchronous? What is a rationale for making async declaration obligatory ?
In async functions await is rewritten to code where .then(...) is used instead of await.
The async modifier marks such a function as one that has to be rewritten and with that await is supported.
Without async you would have to write
void main() {
return funcTwo().then((x) {
print(x);
});
}
This is a very simple example but the rewriting can be rather complex when more of the async features are uses, like try/catch, await for(...), ...
One issue is that await was not originally part of the Dart language. To maintain backward compatibility with existing programs that could potentially use await as an identifier, the language designers added a mechanism to explicitly opt-in to using the new await keyword: by adding a (previously invalid) construct to declare a function async.