wanderanimrod
Finding the file descriptor for an open long-lived http connection
Hello hivemind,
Is there way to find the file descriptor associated with a long-lived tcp connection in elixir / erlang? I am using the HTTPoison library (and hence :hackney) for http calls. I need to send the file descriptor to a server. The client-server interaction goes like this:
- Client opens a long-lived http connection to server (using
HTTP GETwith Keep-alive header) - The server accepts the connection and waits for a payload from the client
- The client finds the file descriptor associated with the connection (which is a path on the client’s local file system in
/proc/${PID}/fd) - The client sends the file descriptor to the server.
I couldn’t find any API on HTTPoison or hackney to get connection file descriptors, so I attempted the following:
# start a custom hackney pool with long connection timeout to ensure long-lived connections
:ok = :hackney_pool.start_pool(:my_pool, [timeout: 60000, max_connections: 1])
# Find the PID of `:my_pool`
my_pool_pid = :hackney_pool.find_pool(:my_pool)
# make http request.
{:ok, _} = HTTPoison.get "http://localhost:8000", [], hackney: [pool: :my_pool]
# List all open ports
open_tcp_port =
:erlang.ports()
|> Enum.map(fn p -> :erlang.port_info(p, :connected) end)
|> Enum.find(fn {:connected, p} -> p == my_pool_pid end)
#[
# name: 'tcp_inet',
# links: [#PID<0.285.0>],
# id: 288,
# connected: #PID<0.285.0>,
# input: 0,
# output: 68,
# os_pid: :undefined
#]
# Ask erlang to print out a list of open sockets. Notice that the only open socket has Port=288,
# which is the `id` of `open_tcp_port`.
:inet.i
#Port Module Recv Sent Owner Local Address Foreign Address State Type
#288 inet_tcp 147 68 <0.285.0> localhost:63617 localhost:irdmi CONNECTED(O) STREAM
#:ok
Question
How can I get from the open_tcp_port and / or the socket information from inet.i to a file descriptor path?
Thanks in advance.
Marked As Solved
wanderanimrod
I found a solution.
# start a custom hackney pool with long connection timeout to ensure long-lived connections
:ok = :hackney_pool.start_pool(:my_pool, [timeout: 60000, max_connections: 1])
# Find the PID of `:my_pool`
my_pool_pid = :hackney_pool.find_pool(:my_pool)
# make an http request. This should create a long-lived connection if the server supports it
{:ok, _} = HTTPoison.get "http://localhost:8000", [], hackney: [pool: :my_pool]
# Find the open port associated with the connection
connection_port =
:erlang.ports()
|> Enum.find(
fn port ->
port_info = :erlang.port_info(port)
port_info[:connected] == my_pool_pid
end
)
{:ok, file_descriptor} = :prim_inet.getfd(connection_port)
6
Popular in Questions
Hi,
is there any work on GUI with Elixir, that is similar to Electron/Javascript? My idea is to bundle Phoenix and BEAM into a single se...
New
Hi, I’m using Ubuntu 18.04 and after updating to OTP-24.0 yesterday i have this warning when I run “mix local.hex”:
14:57:30.512 [warn] ...
New
I am trying to figure out how Mix knows whether the environment is test, dev, or prod -- where is this set?
Thanks.
New
Student & New to elixir. Nice language.
I want to convert a english character, e.g. “a”, which is stored in a variable, to it’s asci...
New
Hello, can anybody help here..? I have a list of players and I what to delete an element, but every for loop the list is reverting to ori...
New
The Elixir Typespec docs show the following syntax for keyword lists in typespecs:
# ...
| [key: type] # keyword lis...
New
Hi,
I am new to Elixir. I am trying to use the DateTime component to insert a date into MySQL however the there seems to be no way to fo...
New
Hi guys, nice to meet you to the whole forum, I’m new here, I’m trying to configure visual studio code for elixir, right now the intellis...
New
I’m not a pro in using Regex and can’t figure out why the following behaviour happens, especially if we take into account the difference ...
New
I’ve been re-reading swift book again and noticed that multiline strings there don’t have a trailing line break, unlike in elixir
iex(2)...
New
Other popular topics
Manning 2016 Halloween weekend sale via Deal of the Day
Friday, October 28 - Half off all MEAPs - code WM102816LT
Saturday, October 29 ...
New
Hi, this is for people who, like me, have had some friction using .html.heex templates in VSCode.
The solution seems to be, in a hyphena...
New
I wanted to check elixir version in phoenix because i found that my elixir is 1.5 but when i use Enum.chunk_by it said the function is un...
New
What’s the safe way to decode a JSON string into a struct? I want to avoid calling String.to_atom. Jason.decode can give me a map with st...
New
Hi,
I'm quite new in Elixir and I'm trying to format a string to a PEM format. I have the certificate value like MIIDBTCCAe2...... and ...
New
As promised, the first release candidate of Phoenix 1.3.0 is out! This release focuses on code generators with improved project structure...
New
Using vs code and installed ElixirLS: support and debugger.
And I got an error popped up on start up says
Failed to run ‘elixir’ comma...
New
What is the difference between System.get_env and Application.get_env? For example, what are best practices to use one versus another.
New
None of the current solutions worked well for me, so I went ahead and built a user management system from scratch.
This project took far...
New
Elixir appears to be a superior language to Python. I don’t see any advantage of Python over Elixir. Are there any?
New







