Add some basic webfingering.

This commit is contained in:
Roger Braun 2017-04-28 17:41:12 +02:00
parent 59d4cc6036
commit ca40dda04c
3 changed files with 76 additions and 1 deletions

View file

@ -2,6 +2,8 @@ defmodule Pleroma.Web.WebFinger do
alias Pleroma.XmlBuilder alias Pleroma.XmlBuilder
alias Pleroma.User alias Pleroma.User
alias Pleroma.Web.OStatus alias Pleroma.Web.OStatus
alias Pleroma.Web.XML
require Logger
def host_meta() do def host_meta() do
base_url = Pleroma.Web.base_url base_url = Pleroma.Web.base_url
@ -37,4 +39,39 @@ defmodule Pleroma.Web.WebFinger do
} }
|> XmlBuilder.to_doc |> XmlBuilder.to_doc
end end
# FIXME: Make this call the host-meta to find the actual address.
defp webfinger_address(domain) do
"https://#{domain}/.well-known/webfinger"
end
defp webfinger_from_xml(doc) do
magic_key = XML.string_from_xpath(~s{//Link[@rel="magic-public-key"]/@href}, doc)
"data:application/magic-public-key," <> magic_key = magic_key
topic = XML.string_from_xpath(~s{//Link[@rel="http://schemas.google.com/g/2010#updates-from"]/@href}, doc)
subject = XML.string_from_xpath("//Subject", doc)
salmon = XML.string_from_xpath(~s{//Link[@rel="salmon"]/@href}, doc)
data = %{
magic_key: magic_key,
topic: topic,
subject: subject,
salmon: salmon
}
{:ok, data}
end
def finger(account, getter \\ &HTTPoison.get/3) do
[name, domain] = String.split(account, "@")
address = webfinger_address(domain)
with {:ok, %{status_code: status_code, body: body}} when status_code in 200..299 <- getter.(address, ["Accept": "application/xrd+xml"], [params: [resource: account]]),
doc <- XML.parse_document(body),
{:ok, data} <- webfinger_from_xml(doc) do
{:ok, data}
else
e ->
Logger.debug("Couldn't finger #{account}.")
Logger.debug(e)
{:error, e}
end
end
end end

20
test/fixtures/webfinger.xml vendored Normal file
View file

@ -0,0 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0">
<Subject>acct:shp@social.heldscal.la</Subject>
<Alias>https://social.heldscal.la/user/29191</Alias>
<Alias>https://social.heldscal.la/shp</Alias>
<Alias>https://social.heldscal.la/index.php/user/29191</Alias>
<Alias>https://social.heldscal.la/index.php/shp</Alias>
<Link rel="http://webfinger.net/rel/profile-page" type="text/html" href="https://social.heldscal.la/shp"/>
<Link rel="http://gmpg.org/xfn/11" type="text/html" href="https://social.heldscal.la/shp"/>
<Link rel="describedby" type="application/rdf+xml" href="https://social.heldscal.la/shp/foaf"/>
<Link rel="http://apinamespace.org/atom" type="application/atomsvc+xml" href="https://social.heldscal.la/api/statusnet/app/service/shp.xml"/>
<Link rel="http://apinamespace.org/twitter" href="https://social.heldscal.la/api/"/>
<Link rel="http://specs.openid.net/auth/2.0/provider" href="https://social.heldscal.la/shp"/>
<Link rel="http://schemas.google.com/g/2010#updates-from" type="application/atom+xml" href="https://social.heldscal.la/api/statuses/user_timeline/29191.atom"/>
<Link rel="magic-public-key" href="data:application/magic-public-key,RSA.wQ3i9UA0qmAxZ0WTIp4a-waZn_17Ez1pEEmqmqoooRsG1_BvpmOvLN0G2tEcWWxl2KOtdQMCiPptmQObeZeuj48mdsDZ4ArQinexY2hCCTcbV8Xpswpkb8K05RcKipdg07pnI7tAgQ0VWSZDImncL6YUGlG5YN8b5TjGOwk2VG8=.AQAB"/>
<Link rel="salmon" href="https://social.heldscal.la/main/salmon/user/29191"/>
<Link rel="http://salmon-protocol.org/ns/salmon-replies" href="https://social.heldscal.la/main/salmon/user/29191"/>
<Link rel="http://salmon-protocol.org/ns/salmon-mention" href="https://social.heldscal.la/main/salmon/user/29191"/>
<Link rel="http://ostatus.org/schema/1.0/subscribe" template="https://social.heldscal.la/main/ostatussub?profile={uri}"/>
</XRD>

View file

@ -1,11 +1,29 @@
defmodule Pleroma.Web.WebFingerTest do defmodule Pleroma.Web.WebFingerTest do
use Pleroma.DataCase use Pleroma.DataCase
alias Pleroma.Web.WebFinger
describe "host meta" do describe "host meta" do
test "returns a link to the xml lrdd" do test "returns a link to the xml lrdd" do
host_info = Pleroma.Web.WebFinger.host_meta host_info = WebFinger.host_meta()
assert String.contains?(host_info, Pleroma.Web.base_url) assert String.contains?(host_info, Pleroma.Web.base_url)
end end
end end
describe "fingering" do
test "returns the info for a user" do
user = "shp@social.heldscal.la"
getter = fn(_url, _headers, [params: [resource: ^user]]) ->
{:ok, %{status_code: 200, body: File.read!("test/fixtures/webfinger.xml")}}
end
{:ok, data} = WebFinger.finger(user, getter)
assert data.magic_key == "RSA.wQ3i9UA0qmAxZ0WTIp4a-waZn_17Ez1pEEmqmqoooRsG1_BvpmOvLN0G2tEcWWxl2KOtdQMCiPptmQObeZeuj48mdsDZ4ArQinexY2hCCTcbV8Xpswpkb8K05RcKipdg07pnI7tAgQ0VWSZDImncL6YUGlG5YN8b5TjGOwk2VG8=.AQAB"
assert data.topic == "https://social.heldscal.la/api/statuses/user_timeline/29191.atom"
assert data.subject == "acct:shp@social.heldscal.la"
assert data.salmon == "https://social.heldscal.la/main/salmon/user/29191"
end
end
end end