Fullrate / acs_ex

An Elixir implementation of the Auto Configuration Server described in the TR-069 specification
11 stars 3 forks source link

Document #4

Closed hadadiashkan closed 5 months ago

hadadiashkan commented 5 years ago

Is there any documentation for this project?

jdalberg commented 5 years ago

I didn't think any was needed. What in particular is confusing about it?

hadadiashkan commented 5 years ago

i want to know how to run it. could you please help me with that?

jdalberg commented 5 years ago

In the readme there is a link to an example project that uses acs_ex right at the bottom. "my_acs" is the project. The idea is that acs_ex takes care of the "stomach" of the ACS handling, and "my_acs" (or whatever you call you elixir project that is you actual acs server) just uses acs_ex and implements the code to handle your specific device logic.

hadadiashkan commented 5 years ago

screenshot from 2019-03-04 12-56-39 when i ran the program, it issues an Error handling request screenshot from 2019-03-04 12-58-30

jdalberg commented 5 years ago

Well. It looks like you are trying to perform a GET request to the base acs endpoint. I dont know what you expected to get back??

The TR-069 spec specifies that requests should be POSTed in as soap.

jdalberg commented 5 years ago

An example of how to send a proper request into the server can be seen in the my_acs test cases.

hadadiashkan commented 5 years ago

how can CPEs connect to this server?

jdalberg commented 5 years ago

You configure the TR-069 endpoint in the devices directly or through dhcp if the cpe supports that, then the CPE's will connect to the port you configured acs_ex to run on, and you should see stuff happening :)

hadadiashkan commented 5 years ago

clipboard-1551700141733 i used your test case but is send me a bad request. i don't know why!

jdalberg commented 5 years ago

Can you provide a trace, for instance with

tcpdump -A -s 0 'tcp port 7547 and (((ip[2:2] - ((ip[0]&0xf)<<2)) - ((tcp[12]&0xf0)>>2)) != 0)'

so i can see what you send into the server...

hadadiashkan commented 5 years ago

capture.zip in this capture body is empty.

hadadiashkan commented 5 years ago

capture_with_body.zip in this capture i filled the body with "plain1" content

jdalberg commented 5 years ago

hmm, that capture looks a litte suspicious.

What does the acs server log when attempting to process the request?

hadadiashkan commented 5 years ago

16:26:07.042 [error] Plug error: CWMP.Parser error: Malformed: Illegal character in prolog

16:26:07.047 [error] Ranch listener :ipv4_listener_7547, connection process #PID<0.498.0>, stream 1 had its request process #PID<0.499.0> exit with reason {{%Plug.Parsers.ParseError{exception: %CWMP.Protocol.Parser.ParseError{message: "Malformed: Illegal character in prolog"}, plug_status: 400}, [{ACS.CWMP.Parser, :parse, 5, [file: 'lib/cwmp_parser.ex', line: 35]}, {Plug.Parsers, :reduce, 7, [file: 'lib/plug/parsers.ex', line: 271]}, {ACS.Handlers.ACS, :plug_builder_call, 2, [file: 'lib/handlers/acs.ex', line: 1]}, {ACS.Handlers.ACS, :call, 2, [file: 'lib/plug/error_handler.ex', line: 64]}, {ACS.ACSHandler, :plug_builder_call, 2, [file: 'lib/acs_handler.ex', line: 1]}, {ACS.ACSHandler, :call, 2, [file: 'lib/plug/error_handler.ex', line: 64]}, {Plug.Cowboy.Handler, :init, 2, [file: 'lib/plug/cowboy/handler.ex', line: 12]}, {:cowboy_handler, :execute, 2, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_handler.erl', line: 41]}]}, {ACS.ACSHandler, :call, [%Plug.Conn{adapter: {Plug.Cowboy.Conn, :...}, assigns: %{}, before_send: [], body_params: %Plug.Conn.Unfetched{aspect: :body_params}, cookies: %Plug.Conn.Unfetched{aspect: :cookies}, halted: false, host: "192.168.40.164", method: "POST", owner: #PID<0.499.0>, params: %Plug.Conn.Unfetched{aspect: :params}, path_info: [], path_params: %{}, port: 7547, private: %{}, query_params: %Plug.Conn.Unfetched{aspect: :query_params}, query_string: "", remote_ip: {192, 168, 40, 166}, req_cookies: %Plug.Conn.Unfetched{aspect: :cookies}, req_headers: [{"accept", "/"}, {"accept-encoding", "gzip, deflate"}, {"cache-control", "no-cache"}, {"connection", "keep-alive"}, {"content-length", "1"}, {"content-type", "text/xml"}, {"cookie", "session="}, {"host", "192.168.40.164:7547"}, {"postman-token", "23562e3c-89d6-4f49-a0e7-21008005838e"}, {"user-agent", "PostmanRuntime/7.1.1"}], request_path: "/", resp_body: nil, resp_cookies: %{}, resp_headers: [{"cache-control", "max-age=0, private, must-revalidate"}], scheme: :http, script_name: [], secret_key_base: nil, state: :unset, status: nil}, [MyAcs.Session]]}} and stacktrace [{Plug.Cowboy.Handler, :init, 2, [file: 'lib/plug/cowboy/handler.ex', line: 20]}, {:cowboy_handler, :execute, 2, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_handler.erl', line: 41]}, {:cowboy_stream_h, :execute, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 296]}, {:cowboy_stream_h, :request_process, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 274]}, {:proc_lib, :init_p_do_apply, 3, [file: 'proc_lib.erl', line: 249]}]

hadadiashkan commented 5 years ago

16:04:17.158 [error] Ranch listener :ipv4_listener_7547, connection process #PID<0.483.0>, stream 1 had its request process #PID<0.484.0> exit with reason {{%FunctionClauseError{args: nil, arity: 4, clauses: nil, function: :do_match, kind: nil, module: ACS.ACSHandler}, [{ACS.ACSHandler, :do_match, [%Plug.Conn{adapter: {Plug.Cowboy.Conn, :...}, assigns: %{}, before_send: [], body_params: %Plug.Conn.Unfetched{aspect: :body_params}, cookies: %Plug.Conn.Unfetched{aspect: :cookies}, halted: false, host: "127.0.0.1", method: "GET", owner: #PID<0.484.0>, params: %Plug.Conn.Unfetched{aspect: :params}, path_info: [], path_params: %{}, port: 7547, private: %{session_handler: MyAcs.Session}, query_params: %Plug.Conn.Unfetched{aspect: :query_params}, query_string: "", remote_ip: {127, 0, 0, 1}, req_cookies: %Plug.Conn.Unfetched{aspect: :cookies}, req_headers: [{"accept", "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,/;q=0.8"}, {"accept-encoding", "gzip, deflate"}, {"accept-language", "en-US,en;q=0.5"}, {"connection", "keep-alive"}, {"host", "127.0.0.1:7547"}, {"upgrade-insecure-requests", "1"}, {"user-agent", "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:65.0) Gecko/20100101 Firefox/65.0"}], request_path: "/", resp_body: nil, resp_cookies: %{}, resp_headers: [{"cache-control", "max-age=0, private, must-revalidate"}], scheme: :http, script_name: [], secret_key_base: nil, state: :unset, status: nil}, "GET", [], "127.0.0.1"], [file: 'lib/acs_handler.ex', line: 42]}, {ACS.ACSHandler, :plug_builder_call, 2, [file: 'lib/acs_handler.ex', line: 1]}, {ACS.ACSHandler, :call, 2, [file: 'lib/plug/error_handler.ex', line: 64]}, {Plug.Cowboy.Handler, :init, 2, [file: 'lib/plug/cowboy/handler.ex', line: 12]}, {:cowboy_handler, :execute, 2, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_handler.erl', line: 41]}, {:cowboy_stream_h, :execute, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 296]}, {:cowboy_stream_h, :request_process, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 274]}, {:proc_lib, :init_p_do_apply, 3, [file: 'proc_lib.erl', line: 249]}]}, {ACS.ACSHandler, :call, [%Plug.Conn{adapter: {Plug.Cowboy.Conn, :...}, assigns: %{}, before_send: [], body_params: %Plug.Conn.Unfetched{aspect: :body_params}, cookies: %Plug.Conn.Unfetched{aspect: :cookies}, halted: false, host: "127.0.0.1", method: "GET", owner: #PID<0.484.0>, params: %Plug.Conn.Unfetched{aspect: :params}, path_info: [], path_params: %{}, port: 7547, private: %{}, query_params: %Plug.Conn.Unfetched{aspect: :query_params}, query_string: "", remote_ip: {127, 0, 0, 1}, req_cookies: %Plug.Conn.Unfetched{aspect: :cookies}, req_headers: [{"accept", "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,/;q=0.8"}, {"accept-encoding", "gzip, deflate"}, {"accept-language", "en-US,en;q=0.5"}, {"connection", "keep-alive"}, {"host", "127.0.0.1:7547"}, {"upgrade-insecure-requests", "1"}, {"user-agent", "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:65.0) Gecko/20100101 Firefox/65.0"}], request_path: "/", resp_body: nil, resp_cookies: %{}, resp_headers: [{"cache-control", "max-age=0, private, must-revalidate"}], scheme: :http, script_name: [], secret_key_base: nil, state: :unset, status: nil}, [MyAcs.Session]]}} and stacktrace [{Plug.Cowboy.Handler, :init, 2, [file: 'lib/plug/cowboy/handler.ex', line: 20]}, {:cowboy_handler, :execute, 2, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_handler.erl', line: 41]}, {:cowboy_stream_h, :execute, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 296]}, {:cowboy_stream_h, :request_process, 3, [file: '/home/ashkan/my_acs/deps/cowboy/src/cowboy_stream_h.erl', line: 274]}, {:proc_lib, :init_p_do_apply, 3, [file: 'proc_lib.erl', line: 249]}]

jdalberg commented 5 years ago

Illegal character in prolog is an erlsom error, the xml parser for erlang, that parses the XML for the CWMP module. This means that the XML you client sends to the ACS is not "clean"

What client are you using to send the POST?

I would probably just use curl for starters....

hadadiashkan commented 5 years ago

postman

jdalberg commented 5 years ago

I dont know what that is....

jdalberg commented 5 years ago

I tried to clone the my_acs project at did "mix deps.get" and "mix test" and got an error. I fixed that, so if you pull from my_acs you should be able to run the tests. Then you can trace while running the tests and compare to what postman does.

hadadiashkan commented 5 years ago

Do you set any credential for CWMP login?(server-side)

hadadiashkan commented 5 years ago

ip-phone client.zip i connected an IP-phone client to this server, but i think it didn't work properly.

jdalberg commented 5 years ago

Do you set any credential for CWMP login?(server-side)

You mean ACS login. No.

jdalberg commented 5 years ago

ip-phone client.zip i connected an IP-phone client to this server, but i think it didn't work properly.

I dont understand the traces you attach, it has all kinds of weird characters in them. If that is an expression of data in the xml, then i can certainly understand why that would raise a parse error.

hadadiashkan commented 5 years ago

can this project enable to set login? to authenticate client

jdalberg commented 5 years ago

It can. It's just never something i have needed.

hadadiashkan commented 5 years ago

Is there any documentation to explain what APIs exist? or do you have plan for that in the future?

jdalberg commented 5 years ago

The way I have built it is so that acs_ex module only takes care of the actual TR-069 messaging. Any API's or any other specific code related to your organization and your devices is up to you. So our own version of "my_acs" is very large and has all the API's we need to interact with the devices.

What you need will most likely differ quite extensively from that, so building a generalized api is hard.

I have thought about expanding the "my_acs" example with a simple API that allows you to do simple stuff like setting parameter values and so on, just to show how it could be done.

jdalberg commented 5 years ago

I tried to incorporate the inform from your device in the cwmp_ex module, which is the one that parses all messages.

The testcase failed with

{:error, %RuntimeError{message: "timestring '2019-03-05T11:54::14' is unparseable: :invalid_format"}}

As you can see, that timestring looks suspicious. The manufacturer of the device should fix that.

Thats why you get the parser error.