hello slack
parent
96e1b700e9
commit
79521805f1
|
@ -74,16 +74,18 @@ defmodule Farmbot.HTTP do
|
|||
end
|
||||
end
|
||||
|
||||
def download_file(ctx, url, path) do
|
||||
case get(ctx, url, "", [], file: path) do
|
||||
def download_file(ctx, url, path, payload \\ "", headers \\ [])
|
||||
def download_file(ctx, url, path, payload, headers) do
|
||||
case get(ctx, url, payload, headers, file: path) do
|
||||
{:ok, %Response{status_code: code}} when is_2xx(code) -> {:ok, path}
|
||||
{:ok, %Response{} = resp} -> {:error, resp}
|
||||
{:error, reason} -> {:error, reason}
|
||||
end
|
||||
end
|
||||
|
||||
def download_file!(ctx, url, path) do
|
||||
case download_file(ctx, url, path) do
|
||||
def download_file!(ctx, url, path, payload \\ "", headers \\ [])
|
||||
def download_file!(ctx, url, path, payload, headers) do
|
||||
case download_file(ctx, url, path, payload, headers) do
|
||||
{:ok, path} -> path
|
||||
{:error, reason} -> raise Error, reason
|
||||
end
|
||||
|
@ -204,10 +206,12 @@ defmodule Farmbot.HTTP do
|
|||
def handle_info(%AsyncChunk{chunk: chunk, id: ref}, state) do
|
||||
case state.requests[ref] do
|
||||
%Buffer{} = buffer ->
|
||||
Process.cancel_timer(buffer.timeout)
|
||||
timeout = Process.send_after(self(), {:timeout, ref}, 30_000)
|
||||
maybe_log_progress(buffer)
|
||||
maybe_stream_to_file(buffer.file, buffer.status_code, chunk)
|
||||
HTTPoison.stream_next(%AsyncResponse{id: ref})
|
||||
{:noreply, %{state | requests: %{state.requests | ref => %{buffer | data: buffer.data <> chunk}}}}
|
||||
{:noreply, %{state | requests: %{state.requests | ref => %{buffer | data: buffer.data <> chunk, timeout: timeout}}}}
|
||||
nil -> {:noreply, state}
|
||||
end
|
||||
end
|
||||
|
@ -300,11 +304,12 @@ defmodule Farmbot.HTTP do
|
|||
|
||||
defp do_normal_request({method, url, body, headers, opts, from}, file, state) do
|
||||
case HTTPoison.request(method, url, body, headers, opts) do
|
||||
{:ok, %HTTPoison.Response{status_code: code, headers: resp_headers}} when code in @redirect_status_codes ->
|
||||
{:ok, %HTTPoison.Response{status_code: code, headers: resp_headers} = resp} when code in @redirect_status_codes ->
|
||||
redir = Enum.find_value(resp_headers, fn({header, val}) -> if header == "Location", do: val, else: false end)
|
||||
if redir do
|
||||
do_normal_request({method, redir, body, headers, opts, from}, file, state)
|
||||
else
|
||||
debug_log("Failed to redirect: #{inspect resp}")
|
||||
GenServer.reply(from, {:error, :no_server_for_redirect})
|
||||
{:noreply, state}
|
||||
end
|
||||
|
@ -360,10 +365,18 @@ defmodule Farmbot.HTTP do
|
|||
|
||||
defp finish_request(%Buffer{status_code: status_code} = buffer, state) when status_code in @redirect_status_codes do
|
||||
debug_log "#{inspect Tuple.delete_at(buffer.from, 0)} Trying to redirect: (#{status_code})"
|
||||
redir = Enum.find_value(buffer.headers, fn({header, val}) -> if header == "Location", do: val, else: false end)
|
||||
redir = Enum.find_value(buffer.headers,
|
||||
fn({header, val}) ->
|
||||
case header do
|
||||
"Location" -> val
|
||||
"location" -> val
|
||||
_ -> false
|
||||
end
|
||||
end)
|
||||
if redir do
|
||||
do_redirect_request(buffer, redir, state)
|
||||
else
|
||||
debug_log("Failed to redirect: #{inspect buffer}")
|
||||
GenServer.reply(buffer.from, {:error, :no_server_for_redirect})
|
||||
{:noreply, state}
|
||||
end
|
||||
|
|
|
@ -280,7 +280,12 @@ defmodule Farmbot.System.Network do
|
|||
|
||||
else
|
||||
|
||||
def maybe_setup_rollbar(_), do: Logger.info ">> Not Setting up rollbar!"
|
||||
def maybe_setup_rollbar(_) do
|
||||
Logger.info ">> Not Setting up rollbar!"
|
||||
Logger.info ">> Setting up slack updater"
|
||||
Farmbot.System.NervesCommon.Updates.Slack.start_link(Farmbot.Context.new())
|
||||
:ok
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
|
|
|
@ -0,0 +1,130 @@
|
|||
defmodule Farmbot.System.NervesCommon.Updates.Slack do
|
||||
@moduledoc """
|
||||
Development module for auto flashing fw updates.
|
||||
"""
|
||||
|
||||
require Logger
|
||||
use GenServer
|
||||
alias Farmbot.{Context, HTTP, DebugLog}
|
||||
use DebugLog
|
||||
|
||||
defmodule RTMSocket do
|
||||
def start_link(url, cb) do
|
||||
pid = spawn(__MODULE__, :socket_init, [url, cb])
|
||||
{:ok, pid}
|
||||
end
|
||||
|
||||
def socket_init("wss://" <> url, cb) do
|
||||
[domain | rest] = String.split(url, "/")
|
||||
domain
|
||||
|> Socket.Web.connect!(secure: true, path: "/" <> Enum.join(rest, "/"))
|
||||
|> socket_loop(cb)
|
||||
end
|
||||
|
||||
def socket_init("ws://" <> url, cb) do
|
||||
[domain | rest] = String.split(url, "/")
|
||||
domain
|
||||
|> Socket.Web.connect!(secure: false, path: "/" <> Enum.join(rest, "/"))
|
||||
|> socket_loop(cb)
|
||||
end
|
||||
|
||||
defp socket_loop(socket, cb) do
|
||||
case socket |> Socket.Web.recv! do
|
||||
{:text, data} -> data |> Poison.decode! |> handle_data(socket, cb)
|
||||
{:ping, _} -> Socket.Web.send!(socket, {:pong, ""})
|
||||
end
|
||||
|
||||
receive do
|
||||
{:stop, _reason} ->
|
||||
term_msg = %{
|
||||
type: "message",
|
||||
id: 2,
|
||||
channel: "C58DCU4A3",
|
||||
text: ":farmbot-genesis: #{node()} Disconnected!"
|
||||
} |> Poison.encode!
|
||||
Socket.Web.send!(socket, {:text, term_msg})
|
||||
Socket.Web.close(socket)
|
||||
data ->
|
||||
Socket.Web.send!(socket, {:text, Poison.encode!(data)})
|
||||
socket_loop(socket, cb)
|
||||
after 500 -> socket_loop(socket, cb)
|
||||
end
|
||||
end
|
||||
|
||||
defp handle_data(%{"type" => "hello"}, socket, _) do
|
||||
Logger.info ">> is connected to slack!", type: :success
|
||||
msg = %{
|
||||
type: "message",
|
||||
id: 1,
|
||||
channel: "C58DCU4A3",
|
||||
text: ":farmbot-genesis: #{node()} Connected!"
|
||||
} |> Poison.encode!()
|
||||
Socket.Web.send!(socket, {:text, msg})
|
||||
end
|
||||
|
||||
defp handle_data(msg, _socket, cb), do: send(cb, {:socket, msg})
|
||||
end
|
||||
|
||||
@token System.get_env("SLACK_TOKEN")
|
||||
|
||||
def start_link(%Context{} = context, opts \\ []) do
|
||||
GenServer.start_link(__MODULE__, {context, @token}, opts)
|
||||
end
|
||||
|
||||
def init({_, nil}) do
|
||||
:ignore
|
||||
end
|
||||
|
||||
def init({context, token}) do
|
||||
debug_log "Using token: #{token}"
|
||||
url = "https://slack.com/api/rtm.connect"
|
||||
payload = {:multipart, [{"token", token}]}
|
||||
headers = [{'User-Agent', 'Farmbot HTTP Adapter'}]
|
||||
case HTTP.post(context, url, payload, headers) do
|
||||
{:ok, %{status_code: 200, body: body}} ->
|
||||
{:ok, rtm_socket} =
|
||||
body
|
||||
|> Poison.decode!
|
||||
|> ensure_good_login
|
||||
|> Map.get("url")
|
||||
|> RTMSocket.start_link(self())
|
||||
{:ok, %{rtm_socket: rtm_socket, context: context, token: token}}
|
||||
err ->
|
||||
debug_log "Failed to get RTM Auth: #{inspect err}"
|
||||
:ignore
|
||||
end
|
||||
end
|
||||
|
||||
defp ensure_good_login(%{"ok" => true} = msg), do: msg
|
||||
defp ensure_good_login(msg) do
|
||||
raise("failed to auth: #{inspect msg}")
|
||||
end
|
||||
|
||||
def handle_info({:socket, %{"channel" => "C41SHHGQ5",
|
||||
"file" => %{"url_private_download" => dl_url,
|
||||
"name" => name,
|
||||
"channels" => ["C41SHHGQ5"],
|
||||
}
|
||||
}
|
||||
} = msg, state)
|
||||
do
|
||||
if Path.extname(name) == ".fw" do
|
||||
Logger.info ">> is downloading and applying an immage from slack!", type: :busy
|
||||
path = HTTP.download_file!(state.context, dl_url, "/tmp/#{name}", [], [{'Authorization', 'Bearer #{state.token}'}])
|
||||
Farmbot.System.Updates.setup_post_update()
|
||||
Nerves.Firmware.upgrade_and_finalize(path)
|
||||
Farmbot.System.reboot()
|
||||
{:stop, :normal, state}
|
||||
else
|
||||
{:noreply, state}
|
||||
end
|
||||
end
|
||||
|
||||
def handle_info({:socket, _msg}, state) do
|
||||
{:noreply, state}
|
||||
end
|
||||
|
||||
def terminate(reason, state) do
|
||||
send state.rtm_socket, {:stop, reason}
|
||||
end
|
||||
end
|
|
@ -19,7 +19,6 @@ defmodule Mix.Tasks.Farmbot.Slack do
|
|||
commit = Mix.Project.config[:commit]
|
||||
fw_file = Path.join(["images", "#{Mix.env()}", "#{target}",
|
||||
(if signed?, do: "#{otp_app}-signed.fw", else: "#{otp_app}.fw")])
|
||||
# fw_file = "/tmp/hello.txt"
|
||||
|
||||
unless File.exists?(fw_file) do
|
||||
Mix.raise "Could not find firmware: #{fw_file}"
|
||||
|
@ -34,7 +33,6 @@ defmodule Mix.Tasks.Farmbot.Slack do
|
|||
|
||||
url = "https://slack.com/api/files.upload"
|
||||
form_data = %{
|
||||
"file" => "replace_me",
|
||||
:file => fw_file,
|
||||
"token" => token,
|
||||
"channels" => "embedded-systems",
|
||||
|
|
2
mix.exs
2
mix.exs
|
@ -110,6 +110,7 @@ defmodule Farmbot.Mixfile do
|
|||
:timex, # Timex needs to start AFTER farmbot, so we can set up its dirs,
|
||||
:inets,
|
||||
:ssl,
|
||||
:socket,
|
||||
:redix,
|
||||
:eex,
|
||||
:httpoison
|
||||
|
@ -143,6 +144,7 @@ defmodule Farmbot.Mixfile do
|
|||
{:exjsx, "~> 3.2", override: true},
|
||||
{:rsa, "~> 0.0.1"},
|
||||
{:httpoison, "~> 0.12"},
|
||||
{:socket, "~> 0.3"},
|
||||
# {:hackney, path: "../hackney", override: true},
|
||||
|
||||
# MQTT stuff
|
||||
|
|
1
mix.lock
1
mix.lock
|
@ -63,6 +63,7 @@
|
|||
"redix": {:hex, :redix, "0.5.1", "2bf874a186cc759791b8defdd0bfaa752784716bd48241f6aa972a20e7f95745", [:mix], [{:connection, "~> 1.0", [hex: :connection, optional: false]}]},
|
||||
"rollbax": {:hex, :rollbax, "0.8.2", "204a47a83fe32745def19ea0307b297395c00315fb85f30dfda04d5009b5ecb9", [:mix], [{:hackney, "~> 1.1", [hex: :hackney, repo: "hexpm", optional: false]}, {:poison, "~> 1.4 or ~> 2.0 or ~> 3.0", [hex: :poison, repo: "hexpm", optional: false]}], "hexpm"},
|
||||
"rsa": {:hex, :rsa, "0.0.1", "a63069f88ce342ffdf8448b7cdef4b39ba7dee3c1510644a39385c7e63ba246f", [:mix], []},
|
||||
"socket": {:hex, :socket, "0.3.12", "4a6543815136503fee67eff0932da1742fad83f84c49130c854114153cc549a6", [:mix], []},
|
||||
"ssl_verify_fun": {:hex, :ssl_verify_fun, "1.1.1", "28a4d65b7f59893bc2c7de786dec1e1555bd742d336043fe644ae956c3497fbe", [:make, :rebar], []},
|
||||
"syslog": {:hex, :syslog, "1.0.2", "9cf72c0986675a170c03b210e49700845a0f7b61e96d302a3ba0df82963daf60", [:rebar], []},
|
||||
"system_registry": {:hex, :system_registry, "0.1.2", "b6dba36c575786f1848e18a1155a2b6bd82f607f0ae9dc88185d6b7dc3fcdf60", [:mix], []},
|
||||
|
|
Loading…
Reference in New Issue