(ES 8.6.2, W10)
In Insomnia, when I try to delete a non-existent index, using command DELETE and url https://localhost:9500/my_test_index, I always seem to get a JSON object like this:
{
"error": {
"root_cause": [
...
"status": 404
}
Similarly when I do the above in Python, using requests
, I get the above response.
But when I run a reqwest
request (in Rust) doing that same request I sometimes get the above but often get this:
{
"acknowledged": true
}
The reason I'm doing this is to delete the index if it exists. Either 200 or 404 would therefore be acceptable status codes. But if I get "acknowledged", true or false, I don't know what that means: it's true
even if the index doesn't exist.
This is all happening on a local machine, with one shard. At the current time there are no other indices in my shard. When I create this index, it has a yellow status. So my server/shard seem to be healthy enough.
Can anyone suggest why this might be happening? Might "acknowledged" mean in this case that the server is busy (on a previous command)? Is it possible that Rust's reqwest
code works faster than Python?
Edit
I seem to have detected a pattern: I run the caller Python program, which calls the Rust module, and I get this unexplained result, i.e. response.text()
is "{"acknowledged": true}". Then I run it again and I get an expected response, with "error" and "status" keys. Then I run again and I get the unexplained result, and so on. I.e. there seems to be an alternation between the 2.
Edit2
If I get this "{ "acknowledged": true }" response.text()
, and then repeat the command (whether or not after waiting for 1 ms), it seems that I always get the expected type of response (with "status" key) on the second attempt.
It's funny how this only seems to occur using Rust, not Python. I wonder what the explanation can be. Reading around I see some stuff about "nodes" possibly taking time to respond in the kind of way you expect. Quite strange: would like to know if an expert can suggest what might be going on.
Rust code
As requested. My Rust code takes place inside a utilities function, which uses the duang
crate to permit optional/named parameters:
duang!(
pub fn reqwest_call<T: serde::de::DeserializeOwned + std::fmt::Debug>(url: &str, method: reqwest::Method = reqwest::Method::GET, timeout: u64 = 5_000,
acceptable_status_codes: Vec<u16> = vec![200], content_type: &str = "application/json", body_str: &str = "")
-> Result<T, Box<dyn std::error::Error>> {
let mut error_details = format!(
"=> url was |{url}|\n=> method was {method}\n=> content type was {content_type}\n=> timeout was {timeout}\n=> body\n|");
if body_str.len() <= 200 {
error_details.push_str(body_str);
}
else {
error_details.push_str(&(body_str.to_string()[0..200]));
error_details.push_str("...");
};
error_details.push_str("|\n\n");
let response_result = get_reqwest_client(timeout)?
.request(method, url)
.header("Content-type", content_type)
.body(body_str.to_string())
.basic_auth("mike12", Some("mike12"))
.send();
let response = match response_result {
Ok(response) => response,
Err(e) => {
error!("{e}\n{error_details}\n{}", Backtrace::force_capture());
return Err(Box::new(e))
}
};
...
... this in turn calls another utility get_reqwest_client
which delivers a reqwest.blocking.Client
with the specified timeout. The timeout is currently 5 seconds (see default parameter in the above). No timeout error is happening. If it was, send
would send us to the Err
branch in the above and there'd be no examination of any returned JSON object.
The actual Rust call to my utility method:
let url = format!("{ES_URL}/{}", &op_handler.index_name);
#[derive(Deserialize, Debug)]
struct DeleteResponse {
status: usize
}
let acceptable_status_codes: Vec<u16> = vec![200, 404];
let _: DeleteResponse = match reqwest_call!(&url, reqwest::Method::DELETE,
acceptable_status_codes=acceptable_status_codes) {
Ok(response) => {
...
Err(e) => {
...
/* this part will reveal the message of error "e": namely
that the JSON does not have a key "status", which it must have: otherwise
it can't be interpreted (cast) as a `DeleteResponse` `struct`.*/
In most cases you will get with 404 or 200 with
"acknowledged": true
. You will get"acknowledged": false
when index is found and the delete operation is initiated but it takes too long because master node is busy and cannot process the request within the specified timeout. This behavior is not client-specific and there should be no difference between python and rust responses unless you do something different in yourrequest
call.I tried reproducing your situation, unfortunately you omitted some pretty important parts of your code but if you put a print statement after
.send();
I get something like this:And if I put another print statement after match and take a look at response.bytes() you will see something like this:
So if I replace ... at the end of reqwest with something like
I get back
Ok(DeleteResponse { status: 404 })
in the caller. It seems like everything is working as expected. What do you get?