httr将工作中的Python连接翻译为R。

huangapple go评论63阅读模式
英文:

httr translating working python connection to r

问题

Here's the translation of the code parts you provided:

Python code:

import requests
import random
import os
import pandas as pd
from rdkit import Chem

upload_url = 'site name'

def predict_pka(smi):
    param = {"Smiles": ("tmg", smi)}
    headers = {'token': 'tokenstring'}
    response = requests.post(url=upload_url, files=param, headers=headers)
    jsonbool = int(response.headers['ifjson'])
    if jsonbool == 1:
        res_json = response.json()
        if res_json['status'] == 200:
            pka_datas = res_json['gen_datas']
            return pka_datas
        else:
            raise RuntimeError("Error for prediction")
    else:
        raise RuntimeError("Error for prediction")

if __name__ == "__main__":
    smi = "CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl"
    data_pka = predict_pka(smi)
    print(data_pka)

R code:

getPKA <- function(){
  upload_url <- "site name"
  
  param <- rjson::toJSON(list('Smiles' = c("tmg", "CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl")))
  
  response <- httr::POST(url = upload_url, 
                        httr::add_headers(                          
                          'token' = 'tokenstring'
                        ),
                        encode = c("multipart", "form", "json", "raw"),
                        httr::content_type_json(),
                        body = param, 
                        httr::verbose()
  )
  
  return(response)
}

Please note that the square brackets in R are used to define lists, which is equivalent to Python's normal brackets for defining dictionaries. The format of param in both versions should work correctly for sending a JSON request.

The error you're encountering might be related to the server's response, which is an internal server error (HTTP 500). You might need to check with the server administrators or consult their API documentation for further troubleshooting.

英文:

For a project i am trying to access data produced from an online model/algorithm. The owners provide the python code to access this data. This is as follows:

import requests
import random
import os
import pandas as pd
from rdkit import Chem

upload_url=r&#39;site name&#39;

def predict_pka(smi):
    param={&quot;Smiles&quot; : (&quot;tmg&quot;, smi)}
    headers={&#39;token&#39;:&#39;tokenstring&#39;}
    response=requests.post(url=upload_url, files=param, headers=headers)
    jsonbool=int(response.headers[&#39;ifjson&#39;])
    if jsonbool==1:
        res_json=response.json()
        if res_json[&#39;status&#39;] == 200:
            pka_datas = res_json[&#39;gen_datas&#39;]
            return pka_datas
        else:
            raise RuntimeError(&quot;Error for prediction&quot;)
    else:
        raise RuntimeError(&quot;Error for prediction&quot;)
        
if __name__==&quot;__main__&quot;:
    smi = &quot;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&quot;
    data_pka = predict_pka(smi)
    print(data_pka)

I took out the actual url and the token, since i don't know if its responsible to share those. This code works from R studio and using python, i can get the data.

However i want to get the data using an R script, so i tried translating the code to R:

getPKA = function(){
  upload_url=&quot;site name&quot;
  
  param = rjson::toJSON(list(&#39;Smiles&#39; = c(&quot;tmg&quot;, &quot;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&quot;)))

  response = httr::POST(url = upload_url, 
                        httr::add_headers(                          
                        &#39;token&#39; = &#39;tokenstring&#39;
                        ),
                        encode = c(&quot;multipart&quot;, &quot;form&quot;, &quot;json&quot;, &quot;raw&quot;),
                        httr::content_type_json(),
                        body = param, 
                        httr::verbose()
  )

  return(response)
}

When i run the R code, i get the following output:

-&gt; POST /modules/upload0/ HTTP/1.1
-&gt; Host: host
-&gt; User-Agent: libcurl/7.84.0 r-curl/5.0.0 httr/1.4.5
-&gt; Accept-Encoding: deflate, gzip
-&gt; Accept: application/json, text/xml, application/xml, */*
-&gt; token: tokenstring
-&gt; Content-Type: application/json
-&gt; Content-Length: 56
-&gt; 
&gt;&gt; {&quot;Smiles&quot;:[&quot;tmg&quot;,&quot;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&quot;]}

&lt;- HTTP/1.0 500 INTERNAL SERVER ERROR
&lt;- Content-Type: text/html; charset=utf-8
&lt;- X-XSS-Protection: 0
&lt;- Connection: close
&lt;- Server: Werkzeug/1.0.1 Python/3.6.12
&lt;- Date: Sat, 13 May 2023 10:28:53 GMT
&lt;- 

Once again i redacted the token and the host.

I got to this R code by reading up a bit on both the python requests package and the httr package, however i don't know much about API connections or web connections in general and i only need it for this data.

I think it might have to do with the param format.
When i print param in the python code i get this:
{&#39;Smiles&#39;: (&#39;tmg&#39;, &#39;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&#39;)}
while if i print it in the R code i get this: {&quot;Smiles&quot;:[&quot;tmg&quot;,&quot;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&quot;]}.
Normal brackets are used in the python version and square brackets are used in the R version.

I don't know if this is actually the problem or how to change this. I tried using different list types (vector, list) and i tried directly using the line {&#39;Smiles&#39;: (&#39;tmg&#39;, &#39;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&#39;)} from the python code as a character string in the body, but i get the same error.

If i print the response itself (or the content using content(response)), it says: AttributeError: &#39;NoneType&#39; object has no attribute &#39;filename&#39; among the html file contents.

I do see a lot of questions on stackoverflow with similar questions, and i tried copying their code and molding it for my needs, but it does not really change anything.

thank you for your time!

答案1

得分: 1

这个请求使用 requests 发送一个多部分编码的文件,请求的示例如下:

POST / HTTP/1.1
Host: localhost:1234
User-Agent: python-requests/2.28.2
Accept-Encoding: gzip, deflate, br
Accept: */*
Connection: keep-alive
token: tokenstring
Content-Length: 176
Content-Type: multipart/form-data; boundary=2202e29dea10e9ab00dcf55c67ed1817

--2202e29dea10e9ab00dcf55c67ed1817
Content-Disposition: form-data; name="Smiles"; filename="tmg"

CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl
--2202e29dea10e9ab00dcf55c67ed1817--

使用 httr2 / curl 库,请求应该类似于以下内容:

library(httr2)

getPKA <- function(smi){
  upload_url <- "site name"
  
  # 似乎需要从磁盘读取实际文件以包括 filename="tmg"
  tmg_path <- file.path(tempdir(), "tmg")
  write(smi, tmg_path) 
  tmg_form_data <- curl::form_file(tmg_path, type = "text/plain")
  
  request(upload_url) %>%
    req_headers(token = "tokenstring") %>%
    req_body_multipart(Smiles = tmg_form_data) %>%
    req_timeout(5) %>%
    req_perform(verbosity = 2) %>%
    resp_body_json()
}
getPKA("CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl")  

# -> POST / HTTP/1.1
# -> Host: localhost:1234
# -> User-Agent: httr2/0.2.2 r-curl/5.0.0 libcurl/7.84.0
# -> Accept: */*
# -> Accept-Encoding: deflate, gzip
# -> token: tokenstring
# -> Content-Length: 220
# -> Content-Type: multipart/form-data; boundary=------------------------744c5a08426eb63b
# -> 
# >> --------------------------744c5a08426eb63b
# >> Content-Disposition: form-data; name="Smiles"; filename="tmg"
# >> Content-Type: text/plain
# >> 
# >> CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl
# >> 
# >> --------------------------744c5a08426eb63b--
# Error:
# ! Timeout was reached: [localhost:1234] Operation timed out after 5001 milliseconds with 0 bytes received

这是你提供的代码和请求的翻译。

英文:

That requests call POSTs a multipart-encoded file and request looks something like this:

POST / HTTP/1.1
Host: localhost:1234
User-Agent: python-requests/2.28.2
Accept-Encoding: gzip, deflate, br
Accept: */*
Connection: keep-alive
token: tokenstring
Content-Length: 176
Content-Type: multipart/form-data; boundary=2202e29dea10e9ab00dcf55c67ed1817

--2202e29dea10e9ab00dcf55c67ed1817
Content-Disposition: form-data; name=&quot;Smiles&quot;; filename=&quot;tmg&quot;

CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl
--2202e29dea10e9ab00dcf55c67ed1817--

With httr2 / curl, this should be close enough:

library(httr2)

getPKA &lt;- function(smi){
  upload_url &lt;- &quot;site name&quot;
  
  # Seems that we need to read actual file from disk to include filename=&quot;tmg&quot; 
  tmg_path &lt;- file.path(tempdir(),&quot;tmg&quot;)
  write(smi,tmg_path) 
  tmg_form_data &lt;- curl::form_file(tmg_path, type = &quot;text/plain&quot;)
  
  request(upload_url) %&gt;% 
    req_headers(token = &quot;tokenstring&quot;) %&gt;% 
    req_body_multipart(Smiles = tmg_form_data) %&gt;% 
    req_timeout(5) %&gt;% 
    req_perform(verbosity = 2) %&gt;% 
    resp_body_json()
}
getPKA(&quot;CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl&quot;)  

#&gt; -&gt; POST / HTTP/1.1
#&gt; -&gt; Host: localhost:1234
#&gt; -&gt; User-Agent: httr2/0.2.2 r-curl/5.0.0 libcurl/7.84.0
#&gt; -&gt; Accept: */*
#&gt; -&gt; Accept-Encoding: deflate, gzip
#&gt; -&gt; token: tokenstring
#&gt; -&gt; Content-Length: 220
#&gt; -&gt; Content-Type: multipart/form-data; boundary=------------------------744c5a08426eb63b
#&gt; -&gt; 
#&gt; &gt;&gt; --------------------------744c5a08426eb63b
#&gt; &gt;&gt; Content-Disposition: form-data; name=&quot;Smiles&quot;; filename=&quot;tmg&quot;
#&gt; &gt;&gt; Content-Type: text/plain
#&gt; &gt;&gt; 
#&gt; &gt;&gt; CCOP(=S)(OCC)OC1=NC(=C(C=C1Cl)Cl)Cl
#&gt; &gt;&gt; 
#&gt; &gt;&gt; --------------------------744c5a08426eb63b--
#&gt; Error:
#&gt; ! Timeout was reached: [localhost:1234] Operation timed out after 5001 milliseconds with 0 bytes received

<sup>Created on 2023-05-13 with reprex v2.0.2</sup>

huangapple
  • 本文由 发表于 2023年5月13日 20:02:58
  • 转载请务必保留本文链接:https://go.coder-hub.com/76242629.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定