How to write output of looped curl command to file - bash

I want to run a curl command every few seconds on a loop and I want the output to be written to a file (appending not overwriting each time it runs). I have to also run it from the CLI
Curl command is like below
curl --location --request POST 'https://api.website.com/Auth/token'
--header 'Content-Type: application/x-www-form-urlencoded'
--header 'Cookie: blablabla'
--data-urlencode 'grant_type=password'
--data-urlencode 'username=username'
--data-urlencode 'password=password
I tried adding a while true; do sleep 2 && at the beginning and > file.txt to output at the end but its not working. I'm sure its probably simple but I'm not very good with bash so any help would be great

You can do this:
while :; do
curl --location --request POST 'https://api.website.com/Auth/token' \
--header 'Content-Type: application/x-www-form-urlencoded' \
--header 'Cookie: blablabla' \
--data-urlencode 'grant_type=password' \
--data-urlencode 'username=username' \
--data-urlencode 'password=password'
sleep 2 || break
done >> file.txt

Related

How to get the exact path of files in a folder using bash script?

I have a folder wherein there are two images
dog.jpeg
dog2.jpeg
and I need to send their path in the following queryImage.
#!/bin/bash
for i in /Users/user/Desktop/Short/*;
do
curl --location --request POST 'some_url' \
--header 'x-api-key: dummy-api-key' \
--form 'maxResults="25"' \
--form 'minConfidence="0.1"' \
**--form 'queryImage=#"$i"'**
done
When I try to give the path directly in the following way, we are able to retrieve the path and we get the required output.
#!/bin/bash
for i in /Users/user/Desktop/Short/*;
do
curl --location --request POST 'some_url' \
--header 'x-api-key: dummy-api-key' \
--form 'maxResults="25"' \
--form 'minConfidence="0.1"' \
**--form 'queryImage=#"/Users/user/Desktop/Short/dog.jpeg"'**
done
What am I giving wrong in the first one? How can we get the exact path in queryImage?
Please help. I am a newbie and can't share the details as this is for an internal project.
Thank you :)
Single quotes prevent the substitution at $i.
Use double quotes instead:
#!/bin/bash
for i in /Users/user/Desktop/Short/*
do
curl --location --request POST 'some_url' \
--header 'x-api-key: dummy-api-key' \
--form 'maxResults="25"' \
--form 'minConfidence="0.1"' \
**--form "queryImage=#'$i'"**
done

How to use Bash command line to curl an API with token and payload as parameters

I am novice and first timer to bash. Trying to run bash under command line to invoke an API, by passing token and payload received from two different APIs and are set as parameters. Below is my command. I am trying to add this bash script to a task in AzureBatch service job.
It has 3 curl requests,
First one (Line#1 in the code snippet below)- gets payload by
calling an API. ---- This is working fine, I am able to verify the
payload using the echo statement following the first curl command.
Second one(Line#3 in the code snippet below) - gets token by
calling the token provider ----- This is working fine as well,
verified using the echo statement.
Third one (Line#5 in the code snippet below),This is the problematic command. I am trying to pass the token and payload received from the above two commands and the curl is not able to resolve them.
both token and payload or not resolving to their values..
My Bash COmmand
/bin/bash -c
"payload=$(curl --location --request GET 'http://url/OutreachData')
&& echo -e \"The value of payload is: "'$payload'"\"
&& token=$(curl --location --request POST 'https://login.microsoftonline.com/<<tenantId>>/oauth2/v2.0/token' --header 'Content-Type: application/x-www-form-urlencoded' --data-urlencode 'client_id=<<clientId>>' --data-urlencode 'scope=api://<<applicationId>>/.default' --data-urlencode 'client_secret=<<clientSecret>>' --data-urlencode 'grant_type=client_credentials' --data-urlencode 'Audience=api://<<applicationId>>'|jq -j '.access_token')
&& echo -e \"value of token is "'$token'"\n\"
&& result=$(curl --location --request POST 'https://url/api/<<Resource>>' --header 'accept: */*' --header 'Content-Type: application/json' --header 'Authorization: Bearer '"'$token'" --data-raw "'$payload'")
&& echo -e \"Result is "'$result'"\""
This is how the third Curl is resolving to, payload and token are not getting replaced as we can see in the authorization header and data-raw elements
++ curl --location --request POST https://url/api/ --header 'accept: /' --header 'Content-Type: application/json' --header 'Authorization: Bearer ' --data-raw ''''''''
There should be no need to explicitly run this with bash -c unless you are in a very constrained environment where you simply cannot run Bash by any other means.
The immediate problem is that code like
bash -c "echo "'$token'" && true"
ends up with $token being single-quoted in the shell which you run bash -c from. But the blazingly obvious fix is to not have this complex quoting in the first place.
payload=$(curl --location --request GET 'http://url/OutreachData')
echo "The value of payload is: '$payload'"
token=$(curl --location --request POST \
'https://login.microsoftonline.com/<<tenantId>>/oauth2/v2.0/token' \
--header 'Content-Type: application/x-www-form-urlencoded' \
--data-urlencode 'client_id=<<clientId>>' \
--data-urlencode 'scope=api://<<applicationId>>/.default' \
--data-urlencode 'client_secret=<<clientSecret>>' \
--data-urlencode 'grant_type=client_credentials' \
--data-urlencode 'Audience=api://<<applicationId>>' |
jq -j '.access_token')
echo "value of token is "'$token'"
result=$(curl --location --request POST \
'https://url/api/<<Resource>>' --header 'accept: */*' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer '"$token" \
--data-raw "$payload")
echo "Result is "'$result'"
If your current shell is not Bash and you need these commands to be run in Bash, a simpler workaround is to put the script in a here document, which drastically simplifies the quoting needs (or if this is in an interactive session, just run bash and run these commands at the interactive Bash prompt, then exit when you no longer want to be in Bash).

How to download file(*.txt or *.pdf) which received from GET api response through Curl command?

I want to download files(*.txt and *.pdf) from Ariba site through GET api request and want to automate the whole download process.
Initially I have used Postman for testing purpose which gives me result in the form of file content.
For eg. test.txt file is present on remote site, after GET request from Postman, the result I am getting, it is in form of content of file, so if 'abc' is written in file, I am getting 'abc' as response from test.txt file.
Now if I click on Send and Download button in Postman it gives me option to download file 'test.txt'
I have to automate this process to send GET response and get required file download at specific location. I am trying to use Curl script for this.
I have written corresponding Curl script and tried to execute it.
It gives me response in the form of file content.
curl -X GET \
'https://openapi.ariba.com/api/approval/v1/prod/invoices/INVASINV6-902/attachments/bnMyMDE5LzA0LzAzLzE1MjkyNDE4MQ==?realm=ProjectName&Content-Disposition=attachement' \
-H 'Accept: */*' \
-H 'Authorization: Bearer 7648d29a-db04-4046-b49c-5daed43a145c' \
-H 'Cache-Control: no-cache' \
-H 'Connection: keep-alive' \
-H 'Host: openapi.ariba.com' \
-H 'accept-encoding: gzip, deflate' \
-H 'apiKey: xxxxxxxxxxxxxxxxxx' \
-H 'cache-control: no-cache'
I want to write a curl script which will download file at specific location.
For eg. Above curl command give content(abc) from file Test.txt and not file Test.txt as output
Really appreciate your helpCurl Get Response
Postman Get Response
Finally I got answer to the question, I just need to remove -X GET from my curl script and at the end add -o to download file name.
Below is the final code:
curl 'https://openapi.ariba.com/api/approval/v1/prod/invoices/INVASINV6-902/attachments/bnMyMDE5LxxxxLzE1MjkyNDE4MQ==?realm=ProjectName' \
-H 'Accept: */*' \
-H 'Authorization: Bearer 77876887-xxxxx-42fb-b865-9cf8ff5c2b25' \
-H 'Cache-Control: no-cache' \
-H 'Connection: keep-alive' \
-H 'Host: openapi.ariba.com' \
-H 'accept-encoding: gzip, deflate' \
-H 'apiKey: XXXXXXXXXXXXXXXX' \
-H 'cache-control: no-cache' \
-H 'Content-Type: application/octet-stream' \
-H "Content-Transfer-Encoding: Binary" \
-o "Test.txt"
Above code give me file downloaded at specific location.
Thanks BlackPearl.

Sending cURL data to multiple URLs

My code consists of the following:
curl -k -X DELETE \
-H "X-Parse-Application-Id: staticid" \
-H "X-Parse-Master-Key: statickey" \
https://mystatic.url/dynamicvalue
I have a list of URLS:
https://mystatic.url/johndylan
https://mystatic.url/marypoppins
etc, included in a tobedeleted.txt file and I would like to modify my cURL code to be something like this (which I've tried but didnt work:
curl -k -X DELETE \
-H "X-Parse-Application-Id: staticid" \
-H "X-Parse-Master-Key: statickey" \
> tobedeleted.txt
or to something like this (which also I've tried but it didnt worked)
curl -k -X DELETE \
-H "X-Parse-Application-Id: staticid" \
-H "X-Parse-Master-Key: statickey" \
https://mystatic.url/$tobedeleted.txt
Note that i want to run the same cURL command, each time for each line of the file, so I guess that I would need something like foreach function, since this is a bash script.
You are going to want something like this:
while read value
do
curl -k -X DELETE \
-H "X-Parse-Application-Id: staticid" \
-H "X-Parse-Master-Key: statickey" \
https://mystatic.url/$value
done < tobedeleted.txt

bash encapsulate command options in variables

I have a bunch of these to test my RESTful API
$CURL \
-v \
-H 'Content-Type: application/json' \
-H 'Accept: application/json' \
-X POST \
-d '{"user":{"email":"user#example.com","password":"secret"}}' \
$URL/$PATH/sessions
I kinda want to shorten it to something like
CURLOPTS="-v -H 'Content-Type: application/json' -H 'Accept: application/json'"
$CURL \
$CURLOPTS \
-X POST \
-d '{"user":{"email":"user#example.com","password":"secret"}}' \
$URL/$PATH/sessions
but the options don't seem to be passed in. Any clues?
Short answer: see BashFAQ #50:'m trying to put a command in a variable, but the complex cases always fail!.
Long answer: Putting commands (or parts of commands) into variables and then getting them back out intact is complicated. The reason your script doesn't work is because of the order in which the shell parses the command line: it parses (and removes) quotes and escapes, then replaces variable values. By the time $CURLOPTS gets replaced, it's too late for the quotes to have their intended effect; instead, they're passed to curl as part of the arguments, which confuses curl greatly.
The solution: store the options in an array rather than a plain string:
CURLOPTS=(-v -H 'Content-Type: application/json' -H 'Accept: application/json')
$CURL \
"${CURLOPTS[#]}" \
-X POST \
-d '{"user":{"email":"user#example.com","password":"secret"}}' \
"$URL/$PATH/sessions"
You can use an array and trigger word splitting
$ set -x
$ CURLOPTS=(-v -H 'Content-Type: application/json' -H 'Accept: application/json')
$ : curl "${CURLOPTS[#]}"
+ : curl -v -H 'Content-Type: application/json' -H 'Accept: application/json'

Resources