Start structural port from Spring Boot to Undertow
This commit is contained in:
32
src/main/java/io/kamax/mxisd/http/IsAPIv1.java
Normal file
32
src/main/java/io/kamax/mxisd/http/IsAPIv1.java
Normal file
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http;
|
||||
|
||||
public class IsAPIv1 {
|
||||
|
||||
public static final String Base = "/_matrix/identity/api/v1";
|
||||
|
||||
public static String getValidate(String medium, String sid, String secret, String token) {
|
||||
// FIXME use some kind of URLBuilder
|
||||
return Base + "/validate/" + medium + "/submitToken?sid=" + sid + "&client_secret=" + secret + "&token=" + token;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,74 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io;
|
||||
|
||||
import io.kamax.matrix.ThreePid;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
public class CredentialsValidationResponse {
|
||||
|
||||
public static class Profile {
|
||||
|
||||
private String displayName;
|
||||
private Set<ThreePid> threePids = new HashSet<>();
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
public Set<ThreePid> getThreePids() {
|
||||
return threePids;
|
||||
}
|
||||
|
||||
public void setThreePids(Set<ThreePid> threePids) {
|
||||
this.threePids = new HashSet<>(threePids);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean success;
|
||||
private String displayName; // TODO remove later, legacy support
|
||||
private Profile profile = new Profile();
|
||||
|
||||
public CredentialsValidationResponse(boolean success) {
|
||||
this.success = success;
|
||||
}
|
||||
|
||||
public boolean isSuccess() {
|
||||
return success;
|
||||
}
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
public void setDisplayName(String displayName) {
|
||||
this.displayName = displayName;
|
||||
this.profile.displayName = displayName;
|
||||
}
|
||||
|
||||
public Profile getProfile() {
|
||||
return profile;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io;
|
||||
|
||||
public class UserDirectorySearchRequest {
|
||||
|
||||
private String by;
|
||||
private String searchTerm;
|
||||
|
||||
public UserDirectorySearchRequest(String searchTerm) {
|
||||
setSearchTerm(searchTerm);
|
||||
}
|
||||
|
||||
public UserDirectorySearchRequest(String type, String searchTerm) {
|
||||
setBy(type);
|
||||
setSearchTerm(searchTerm);
|
||||
}
|
||||
|
||||
public String getBy() {
|
||||
return by;
|
||||
}
|
||||
|
||||
public void setBy(String by) {
|
||||
this.by = by;
|
||||
}
|
||||
|
||||
public String getSearchTerm() {
|
||||
return searchTerm;
|
||||
}
|
||||
|
||||
public void setSearchTerm(String searchTerm) {
|
||||
this.searchTerm = searchTerm;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
public class UserDirectorySearchResult {
|
||||
|
||||
public static UserDirectorySearchResult empty() {
|
||||
return new UserDirectorySearchResult();
|
||||
}
|
||||
|
||||
public static class Result {
|
||||
|
||||
private String displayName;
|
||||
private String avatarUrl;
|
||||
private String userId;
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
public void setDisplayName(String displayName) {
|
||||
this.displayName = displayName;
|
||||
}
|
||||
|
||||
public String getAvatarUrl() {
|
||||
return avatarUrl;
|
||||
}
|
||||
|
||||
public void setAvatarUrl(String avatarUrl) {
|
||||
this.avatarUrl = avatarUrl;
|
||||
}
|
||||
|
||||
public String getUserId() {
|
||||
return userId;
|
||||
}
|
||||
|
||||
public void setUserId(String userId) {
|
||||
this.userId = userId;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
|
||||
Result result = (Result) o;
|
||||
|
||||
if (displayName != null ? !displayName.equals(result.displayName) : result.displayName != null)
|
||||
return false;
|
||||
if (avatarUrl != null ? !avatarUrl.equals(result.avatarUrl) : result.avatarUrl != null) return false;
|
||||
return userId.equals(result.userId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = displayName != null ? displayName.hashCode() : 0;
|
||||
result = 31 * result + (avatarUrl != null ? avatarUrl.hashCode() : 0);
|
||||
result = 31 * result + userId.hashCode();
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private boolean limited;
|
||||
private Set<Result> results = new HashSet<>();
|
||||
|
||||
public boolean isLimited() {
|
||||
return limited;
|
||||
}
|
||||
|
||||
public void setLimited(boolean limited) {
|
||||
this.limited = limited;
|
||||
}
|
||||
|
||||
public Set<Result> getResults() {
|
||||
return results;
|
||||
}
|
||||
|
||||
public void setResults(Set<Result> results) {
|
||||
this.results = results;
|
||||
}
|
||||
|
||||
public void addResult(Result result) {
|
||||
this.results.add(result);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import io.kamax.mxisd.lookup.ThreePidMapping;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
public class ClientBulkLookupAnswer {
|
||||
|
||||
private List<List<String>> threepids = new ArrayList<>();
|
||||
|
||||
public void addAll(Collection<ThreePidMapping> mappings) {
|
||||
for (ThreePidMapping mapping : mappings) {
|
||||
threepids.add(Arrays.asList(mapping.getMedium(), mapping.getValue(), mapping.getMxid()));
|
||||
}
|
||||
}
|
||||
|
||||
public List<List<String>> getThreepids() {
|
||||
return threepids;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,49 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import io.kamax.mxisd.lookup.ThreePidMapping;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class ClientBulkLookupRequest {
|
||||
|
||||
private List<List<String>> threepids = new ArrayList<>();
|
||||
|
||||
public List<List<String>> getThreepids() {
|
||||
return threepids;
|
||||
}
|
||||
|
||||
public void setThreepids(List<List<String>> threepids) {
|
||||
this.threepids = threepids;
|
||||
}
|
||||
|
||||
public void setMappings(List<ThreePidMapping> mappings) {
|
||||
for (ThreePidMapping mapping : mappings) {
|
||||
List<String> threepid = new ArrayList<>();
|
||||
threepid.add(mapping.getMedium());
|
||||
threepid.add(mapping.getValue());
|
||||
threepids.add(threepid);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
public abstract class GenericTokenRequestJson {
|
||||
|
||||
private String client_secret;
|
||||
private int send_attempt;
|
||||
private String next_link;
|
||||
|
||||
public String getSecret() {
|
||||
return client_secret;
|
||||
}
|
||||
|
||||
public int getAttempt() {
|
||||
return send_attempt;
|
||||
}
|
||||
|
||||
public String getNextLink() {
|
||||
return next_link;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
public class KeyValidityJson {
|
||||
|
||||
private boolean valid;
|
||||
|
||||
public KeyValidityJson(boolean isValid) {
|
||||
this.valid = isValid;
|
||||
}
|
||||
|
||||
public boolean isValid() {
|
||||
return valid;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
public class RequestTokenResponse {
|
||||
|
||||
private String sid;
|
||||
|
||||
public RequestTokenResponse() {
|
||||
// for (de)serializers
|
||||
}
|
||||
|
||||
public RequestTokenResponse(String sid) {
|
||||
this.sid = sid;
|
||||
}
|
||||
|
||||
public String getSid() {
|
||||
return sid;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import io.kamax.matrix.ThreePidMedium;
|
||||
|
||||
public class SessionEmailTokenRequestJson extends GenericTokenRequestJson {
|
||||
|
||||
private String email;
|
||||
|
||||
public String getMedium() {
|
||||
return ThreePidMedium.Email.getId();
|
||||
}
|
||||
|
||||
public String getValue() {
|
||||
return email;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import com.google.i18n.phonenumbers.NumberParseException;
|
||||
import com.google.i18n.phonenumbers.PhoneNumberUtil;
|
||||
import com.google.i18n.phonenumbers.Phonenumber;
|
||||
|
||||
public class SessionPhoneTokenRequestJson extends GenericTokenRequestJson {
|
||||
|
||||
private static PhoneNumberUtil phoneUtil = PhoneNumberUtil.getInstance();
|
||||
|
||||
private String country;
|
||||
private String phone_number;
|
||||
|
||||
public String getMedium() {
|
||||
return "msisdn";
|
||||
}
|
||||
|
||||
public String getValue() {
|
||||
try {
|
||||
Phonenumber.PhoneNumber num = phoneUtil.parse(phone_number, country);
|
||||
return phoneUtil.format(num, PhoneNumberUtil.PhoneNumberFormat.E164).replace("+", "");
|
||||
} catch (NumberParseException e) {
|
||||
throw new IllegalArgumentException("Invalid phone number");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import io.kamax.mxisd.lookup.SingleLookupReply;
|
||||
|
||||
public class SingeLookupReplyJson {
|
||||
|
||||
private String address;
|
||||
private String medium;
|
||||
private String mxid;
|
||||
private long not_after;
|
||||
private long not_before;
|
||||
private long ts;
|
||||
|
||||
public SingeLookupReplyJson(SingleLookupReply reply) {
|
||||
this.address = reply.getRequest().getThreePid();
|
||||
this.medium = reply.getRequest().getType();
|
||||
this.mxid = reply.getMxid().getId();
|
||||
this.not_after = reply.getNotAfter().toEpochMilli();
|
||||
this.not_before = reply.getNotBefore().toEpochMilli();
|
||||
this.ts = reply.getTimestamp().toEpochMilli();
|
||||
}
|
||||
|
||||
public String getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public String getMedium() {
|
||||
return medium;
|
||||
}
|
||||
|
||||
public String getMxid() {
|
||||
return mxid;
|
||||
}
|
||||
|
||||
public long getNot_after() {
|
||||
return not_after;
|
||||
}
|
||||
|
||||
public long getNot_before() {
|
||||
return not_before;
|
||||
}
|
||||
|
||||
public long getTs() {
|
||||
return ts;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
public class SuccessStatusJson {
|
||||
|
||||
private boolean success;
|
||||
|
||||
public SuccessStatusJson(boolean success) {
|
||||
this.success = success;
|
||||
}
|
||||
|
||||
public boolean isSuccess() {
|
||||
return success;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.io.identity;
|
||||
|
||||
import io.kamax.mxisd.invitation.IThreePidInviteReply;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class ThreePidInviteReplyIO {
|
||||
|
||||
private String token;
|
||||
private List<Key> public_keys;
|
||||
private String display_name;
|
||||
|
||||
public ThreePidInviteReplyIO(IThreePidInviteReply reply, String pubKey, String publicUrl) {
|
||||
this.token = reply.getToken();
|
||||
this.public_keys = Collections.singletonList(new Key(pubKey, publicUrl));
|
||||
this.display_name = reply.getDisplayName();
|
||||
}
|
||||
|
||||
public String getToken() {
|
||||
return token;
|
||||
}
|
||||
|
||||
public List<Key> getPublic_keys() {
|
||||
return public_keys;
|
||||
}
|
||||
|
||||
public String getDisplay_name() {
|
||||
return display_name;
|
||||
}
|
||||
|
||||
public class Key {
|
||||
private String key_validity_url;
|
||||
private String public_key;
|
||||
|
||||
public Key(String key, String publicUrl) {
|
||||
this.key_validity_url = publicUrl + "/_matrix/identity/api/v1/pubkey/isvalid";
|
||||
this.public_key = key;
|
||||
}
|
||||
|
||||
public String getKey_validity_url() {
|
||||
return key_validity_url;
|
||||
}
|
||||
|
||||
public String getPublic_key() {
|
||||
return public_key;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,129 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.exception.HttpMatrixException;
|
||||
import io.kamax.mxisd.exception.InternalServerError;
|
||||
import io.kamax.mxisd.proxy.Response;
|
||||
import io.undertow.server.HttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import io.undertow.util.HttpString;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.InetSocketAddress;
|
||||
import java.net.URLDecoder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.LinkedList;
|
||||
|
||||
public abstract class BasicHttpHandler implements HttpHandler {
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(BasicHttpHandler.class);
|
||||
|
||||
protected String getRemoteHostAddress(HttpServerExchange exchange) {
|
||||
return ((InetSocketAddress) exchange.getConnection().getPeerAddress()).getAddress().getHostAddress();
|
||||
}
|
||||
|
||||
protected String getQueryParameter(HttpServerExchange exchange, String name) {
|
||||
try {
|
||||
String raw = exchange.getQueryParameters().getOrDefault(name, new LinkedList<>()).peekFirst();
|
||||
return URLDecoder.decode(raw, StandardCharsets.UTF_8.name());
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
throw new InternalServerError(e);
|
||||
}
|
||||
}
|
||||
|
||||
protected String getPathVariable(HttpServerExchange exchange, String name) {
|
||||
return getQueryParameter(exchange, name);
|
||||
}
|
||||
|
||||
protected void writeBodyAsUtf8(HttpServerExchange exchange, String body) {
|
||||
exchange.getResponseSender().send(body, StandardCharsets.UTF_8);
|
||||
}
|
||||
|
||||
protected <T> T parseJsonTo(HttpServerExchange exchange, Class<T> type) {
|
||||
try {
|
||||
return GsonUtil.get().fromJson(IOUtils.toString(exchange.getInputStream(), StandardCharsets.UTF_8), type);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
protected JsonObject parseJsonObject(HttpServerExchange exchange, String key) {
|
||||
try {
|
||||
JsonObject base = GsonUtil.parseObj(IOUtils.toString(exchange.getInputStream(), StandardCharsets.UTF_8));
|
||||
return GsonUtil.getObj(base, key);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
protected void respond(HttpServerExchange ex, int statusCode, JsonElement bodyJson) {
|
||||
respondJson(ex, statusCode, GsonUtil.get().toJson(bodyJson));
|
||||
}
|
||||
|
||||
protected void respond(HttpServerExchange ex, JsonElement bodyJson) {
|
||||
respond(ex, 200, bodyJson);
|
||||
}
|
||||
|
||||
protected void respondJson(HttpServerExchange ex, int status, String body) {
|
||||
ex.setStatusCode(status);
|
||||
ex.getResponseHeaders().put(HttpString.tryFromString("Content-Type"), "application/json");
|
||||
writeBodyAsUtf8(ex, body);
|
||||
}
|
||||
|
||||
protected void respondJson(HttpServerExchange ex, String body) {
|
||||
respondJson(ex, 200, body);
|
||||
}
|
||||
|
||||
protected void respondJson(HttpServerExchange ex, Object body) {
|
||||
respondJson(ex, GsonUtil.get().toJson(body));
|
||||
}
|
||||
|
||||
protected JsonObject buildErrorBody(HttpServerExchange exchange, String errCode, String error) {
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.addProperty("errcode", errCode);
|
||||
obj.addProperty("error", error);
|
||||
obj.addProperty("success", false);
|
||||
log.info("Request {} {} - Error {}: {}", exchange.getRequestMethod(), exchange.getRequestURL(), errCode, error);
|
||||
return obj;
|
||||
}
|
||||
|
||||
protected void respond(HttpServerExchange ex, int status, String errCode, String error) {
|
||||
respond(ex, status, buildErrorBody(ex, errCode, error));
|
||||
}
|
||||
|
||||
protected void handleException(HttpServerExchange exchange, HttpMatrixException ex) {
|
||||
respond(exchange, ex.getStatus(), buildErrorBody(exchange, ex.getErrorCode(), ex.getError()));
|
||||
}
|
||||
|
||||
protected void respond(HttpServerExchange exchange, Response upstream) {
|
||||
exchange.setStatusCode(upstream.getStatus());
|
||||
upstream.getHeaders().forEach((key, value) -> exchange.getResponseHeaders().addAll(HttpString.tryFromString(key), value));
|
||||
writeBodyAsUtf8(exchange, upstream.getBody());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler;
|
||||
|
||||
import io.kamax.mxisd.exception.AccessTokenNotFoundException;
|
||||
import io.kamax.mxisd.util.OptionalUtil;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
|
||||
import java.util.LinkedList;
|
||||
import java.util.Optional;
|
||||
|
||||
public abstract class HomeserverProxyHandler extends BasicHttpHandler {
|
||||
|
||||
protected final static String headerName = "Authorization";
|
||||
protected final static String headerValuePrefix = "Bearer ";
|
||||
private final static String parameterName = "access_token";
|
||||
|
||||
Optional<String> findAccessTokenInHeaders(HttpServerExchange exchange) {
|
||||
return Optional.ofNullable(exchange.getRequestHeaders().getFirst(headerName))
|
||||
.filter(header -> StringUtils.startsWith(header, headerValuePrefix))
|
||||
.map(header -> header.substring(headerValuePrefix.length()));
|
||||
}
|
||||
|
||||
Optional<String> findAccessTokenInQuery(HttpServerExchange exchange) {
|
||||
return Optional.ofNullable(exchange.getQueryParameters().getOrDefault(parameterName, new LinkedList<>()).peekFirst());
|
||||
}
|
||||
|
||||
public Optional<String> findAccessToken(HttpServerExchange exchange) {
|
||||
return OptionalUtil.findFirst(() -> findAccessTokenInHeaders(exchange), () -> findAccessTokenInQuery(exchange));
|
||||
}
|
||||
|
||||
public String getAccessToken(HttpServerExchange exchange) {
|
||||
return findAccessToken(exchange).orElseThrow(AccessTokenNotFoundException::new);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,112 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler;
|
||||
|
||||
import com.google.gson.JsonSyntaxException;
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.exception.*;
|
||||
import io.undertow.server.HttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.apache.http.HttpStatus;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.time.Instant;
|
||||
|
||||
public class SaneHandler extends BasicHttpHandler {
|
||||
|
||||
public static SaneHandler around(HttpHandler h) {
|
||||
return new SaneHandler(h);
|
||||
}
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SaneHandler.class);
|
||||
|
||||
private HttpHandler child;
|
||||
|
||||
public SaneHandler(HttpHandler child) {
|
||||
this.child = child;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
exchange.startBlocking();
|
||||
|
||||
if (exchange.isInIoThread()) {
|
||||
exchange.dispatch(this);
|
||||
} else {
|
||||
try {
|
||||
child.handleRequest(exchange);
|
||||
} catch (IllegalArgumentException e) {
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, GsonUtil.makeObj("error", e.getMessage()));
|
||||
} catch (BadRequestException e) {
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, "M_BAD_REQUEST", e.getMessage());
|
||||
} catch (MappingAlreadyExistsException e) {
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, "M_ALREADY_EXISTS", e.getMessage());
|
||||
} catch (JsonMemberNotFoundException e) {
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, "M_JSON_MISSING_KEYS", e.getMessage());
|
||||
} catch (InvalidResponseJsonException | JsonSyntaxException e) {
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, "M_INVALID_JSON", e.getMessage());
|
||||
} catch (InvalidCredentialsException e) {
|
||||
respond(exchange, HttpStatus.SC_UNAUTHORIZED, "M_UNAUTHORIZED", e.getMessage());
|
||||
} catch (ObjectNotFoundException e) {
|
||||
respond(exchange, HttpStatus.SC_NOT_FOUND, "M_NOT_FOUND", e.getMessage());
|
||||
} catch (NotImplementedException e) {
|
||||
respond(exchange, HttpStatus.SC_NOT_IMPLEMENTED, "M_NOT_IMPLEMENTED", e.getMessage());
|
||||
} catch (FeatureNotAvailable e) {
|
||||
if (StringUtils.isNotBlank(e.getInternalReason())) {
|
||||
log.error("Feature not available: {}", e.getInternalReason());
|
||||
}
|
||||
|
||||
handleException(exchange, e);
|
||||
} catch (InternalServerError e) {
|
||||
if (StringUtils.isNotBlank(e.getInternalReason())) {
|
||||
log.error("Reference #{} - {}", e.getReference(), e.getInternalReason());
|
||||
} else {
|
||||
log.error("Reference #{}", e);
|
||||
}
|
||||
|
||||
handleException(exchange, e);
|
||||
} catch (RemoteLoginException e) {
|
||||
if (e.getErrorBodyMsgResp() != null) {
|
||||
respond(exchange, e.getStatus(), e.getErrorBodyMsgResp());
|
||||
} else {
|
||||
handleException(exchange, e);
|
||||
}
|
||||
} catch (HttpMatrixException e) {
|
||||
respond(exchange, e.getStatus(), buildErrorBody(exchange, e.getErrorCode(), e.getError()));
|
||||
} catch (RuntimeException e) {
|
||||
log.error("Unknown error when handling {}", exchange.getRequestURL(), e);
|
||||
respond(exchange, HttpStatus.SC_INTERNAL_SERVER_ERROR, buildErrorBody(exchange,
|
||||
"M_UNKNOWN",
|
||||
StringUtils.defaultIfBlank(
|
||||
e.getMessage(),
|
||||
"An internal server error occurred. If this error persists, please contact support with reference #" +
|
||||
Instant.now().toEpochMilli()
|
||||
)
|
||||
));
|
||||
} finally {
|
||||
exchange.endExchange();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.as.v1;
|
||||
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
import java.util.LinkedList;
|
||||
import java.util.Optional;
|
||||
|
||||
public abstract class ApplicationServiceHandler extends BasicHttpHandler {
|
||||
|
||||
protected String getToken(HttpServerExchange ex) {
|
||||
return Optional.ofNullable(ex.getQueryParameters()
|
||||
.getOrDefault("access_token", new LinkedList<>())
|
||||
.peekFirst()
|
||||
).orElse("");
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.as.v1;
|
||||
|
||||
import io.kamax.mxisd.as.AppSvcManager;
|
||||
import io.kamax.mxisd.exception.NotFoundException;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
public class AsNotFoundHandler extends ApplicationServiceHandler {
|
||||
|
||||
private final AppSvcManager app;
|
||||
|
||||
public AsNotFoundHandler(AppSvcManager app) {
|
||||
this.app = app;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
app.withToken(getToken(exchange));
|
||||
|
||||
throw new NotFoundException();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.as.v1;
|
||||
|
||||
import io.kamax.mxisd.as.AppSvcManager;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
import java.util.LinkedList;
|
||||
|
||||
public class AsTransactionHandler extends ApplicationServiceHandler {
|
||||
|
||||
public static final String ID = "txnId";
|
||||
public static final String Path = "/_matrix/app/v1/transactions/{" + ID + "}";
|
||||
|
||||
private final AppSvcManager app;
|
||||
|
||||
public AsTransactionHandler(AppSvcManager app) {
|
||||
this.app = app;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
String txnId = exchange.getQueryParameters().getOrDefault(ID, new LinkedList<>()).peekFirst();
|
||||
respondJson(exchange, app.withToken(getToken(exchange))
|
||||
.processTransaction(txnId, exchange.getInputStream()).get());
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.auth;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.auth.AuthManager;
|
||||
import io.kamax.mxisd.auth.UserAuthResult;
|
||||
import io.kamax.mxisd.exception.JsonMemberNotFoundException;
|
||||
import io.kamax.mxisd.http.io.CredentialsValidationResponse;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class RestAuthHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = "/_matrix-internal/identity/v1/check_credentials";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(RestAuthHandler.class);
|
||||
|
||||
private AuthManager mgr;
|
||||
|
||||
public RestAuthHandler(AuthManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
JsonObject authData = parseJsonObject(exchange, "user");
|
||||
if (!authData.has("id") || !authData.has("password")) {
|
||||
throw new JsonMemberNotFoundException("Missing id or password keys");
|
||||
}
|
||||
|
||||
String id = GsonUtil.getStringOrThrow(authData, "id");
|
||||
log.info("Requested to check credentials for {}", id);
|
||||
String password = GsonUtil.getStringOrThrow(authData, "password");
|
||||
|
||||
UserAuthResult result = mgr.authenticate(id, password);
|
||||
CredentialsValidationResponse response = new CredentialsValidationResponse(result.isSuccess());
|
||||
|
||||
if (result.isSuccess()) {
|
||||
response.setDisplayName(result.getDisplayName());
|
||||
response.getProfile().setThreePids(result.getThreePids());
|
||||
}
|
||||
|
||||
JsonElement authObj = GsonUtil.get().toJsonTree(response);
|
||||
respond(exchange, GsonUtil.makeObj("auth", authObj));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.auth.v1;
|
||||
|
||||
import io.kamax.mxisd.auth.AuthManager;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.http.client.methods.CloseableHttpResponse;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
import org.apache.http.impl.client.CloseableHttpClient;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
|
||||
import java.net.URI;
|
||||
|
||||
public class LoginGetHandler extends LoginHandler {
|
||||
|
||||
private AuthManager mgr;
|
||||
private CloseableHttpClient client;
|
||||
|
||||
public LoginGetHandler(AuthManager mgr, CloseableHttpClient client) {
|
||||
this.mgr = mgr;
|
||||
this.client = client;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
URI target = URI.create(exchange.getRequestURL());
|
||||
|
||||
try (CloseableHttpResponse hsResponse = client.execute(new HttpGet(mgr.resolveProxyUrl(target)))) {
|
||||
// TODO deal with headers, content-type, encoding, etc.
|
||||
respondJson(exchange, hsResponse.getStatusLine().getStatusCode(), EntityUtils.toString(hsResponse.getEntity()));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.auth.v1;
|
||||
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
|
||||
public abstract class LoginHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = "/_matrix/client/r0/login";
|
||||
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.auth.v1;
|
||||
|
||||
import io.kamax.mxisd.auth.AuthManager;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
|
||||
import java.net.URI;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
|
||||
public class LoginPostHandler extends LoginHandler {
|
||||
|
||||
private AuthManager mgr;
|
||||
|
||||
public LoginPostHandler(AuthManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
respondJson(exchange, mgr.proxyLogin(
|
||||
URI.create(exchange.getRequestURL()),
|
||||
IOUtils.toString(exchange.getInputStream(), StandardCharsets.UTF_8)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.directory.v1;
|
||||
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.directory.DirectoryManager;
|
||||
import io.kamax.mxisd.http.io.UserDirectorySearchRequest;
|
||||
import io.kamax.mxisd.http.io.UserDirectorySearchResult;
|
||||
import io.kamax.mxisd.http.undertow.handler.HomeserverProxyHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
import java.net.URI;
|
||||
|
||||
public class UserDirectorySearchHandler extends HomeserverProxyHandler {
|
||||
|
||||
public static final String Path = "/_matrix/client/r0/user_directory/search";
|
||||
|
||||
private DirectoryManager mgr;
|
||||
|
||||
public UserDirectorySearchHandler(DirectoryManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
String accessToken = getAccessToken(exchange);
|
||||
UserDirectorySearchRequest searchQuery = parseJsonTo(exchange, UserDirectorySearchRequest.class);
|
||||
URI target = URI.create(exchange.getRequestURL());
|
||||
UserDirectorySearchResult result = mgr.search(target, accessToken, searchQuery.getSearchTerm());
|
||||
|
||||
respondJson(exchange, GsonUtil.get().toJson(result));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.io.identity.ClientBulkLookupAnswer;
|
||||
import io.kamax.mxisd.http.io.identity.ClientBulkLookupRequest;
|
||||
import io.kamax.mxisd.lookup.BulkLookupRequest;
|
||||
import io.kamax.mxisd.lookup.ThreePidMapping;
|
||||
import io.kamax.mxisd.lookup.strategy.LookupStrategy;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class BulkLookupHandler extends LookupHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/bulk_lookup";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SingleLookupHandler.class);
|
||||
|
||||
private LookupStrategy strategy;
|
||||
|
||||
public BulkLookupHandler(LookupStrategy strategy) {
|
||||
this.strategy = strategy;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
ClientBulkLookupRequest input = parseJsonTo(exchange, ClientBulkLookupRequest.class);
|
||||
BulkLookupRequest lookupRequest = new BulkLookupRequest();
|
||||
setRequesterInfo(lookupRequest, exchange);
|
||||
log.info("Got bulk lookup request from {} with client {} - Is recursive? {}",
|
||||
lookupRequest.getRequester(), lookupRequest.getUserAgent(), lookupRequest.isRecursive());
|
||||
|
||||
List<ThreePidMapping> mappings = new ArrayList<>();
|
||||
for (List<String> mappingRaw : input.getThreepids()) {
|
||||
ThreePidMapping mapping = new ThreePidMapping();
|
||||
mapping.setMedium(mappingRaw.get(0));
|
||||
mapping.setValue(mappingRaw.get(1));
|
||||
mappings.add(mapping);
|
||||
}
|
||||
lookupRequest.setMappings(mappings);
|
||||
|
||||
ClientBulkLookupAnswer answer = new ClientBulkLookupAnswer();
|
||||
answer.addAll(strategy.find(lookupRequest));
|
||||
respondJson(exchange, answer);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class EphemeralKeyIsValidHandler extends KeyIsValidHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/pubkey/ephemeral/isvalid";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(EphemeralKeyIsValidHandler.class);
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
log.warn("Ephemeral key was requested but no ephemeral key are generated, replying not valid");
|
||||
|
||||
respondJson(exchange, invalidKey);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
public class HelloHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base;
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
respondJson(exchange, "{}");
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.matrix.crypto.KeyManager;
|
||||
import io.kamax.mxisd.exception.BadRequestException;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class KeyGetHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Key = "key";
|
||||
public static final String Path = IsAPIv1.Base + "/pubkey/{key}";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(KeyGetHandler.class);
|
||||
|
||||
private KeyManager mgr;
|
||||
|
||||
public KeyGetHandler(KeyManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String key = getQueryParameter(exchange, Key);
|
||||
String[] v = key.split(":", 1);
|
||||
String keyType = v[0];
|
||||
int keyId = Integer.parseInt(v[1]);
|
||||
|
||||
if (!"ed25519".contentEquals(keyType)) {
|
||||
throw new BadRequestException("Invalid algorithm: " + keyType);
|
||||
}
|
||||
|
||||
log.info("Key {}:{} was requested", keyType, keyId);
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.addProperty("public_key", mgr.getPublicKeyBase64(keyId));
|
||||
respond(exchange, obj);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.http.io.identity.KeyValidityJson;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
|
||||
public abstract class KeyIsValidHandler extends BasicHttpHandler {
|
||||
|
||||
protected final String validKey = GsonUtil.get().toJson(new KeyValidityJson(true));
|
||||
protected final String invalidKey = GsonUtil.get().toJson(new KeyValidityJson(false));
|
||||
|
||||
}
|
||||
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.lookup.ALookupRequest;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.net.InetSocketAddress;
|
||||
import java.util.Arrays;
|
||||
|
||||
public abstract class LookupHandler extends BasicHttpHandler {
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(LookupHandler.class);
|
||||
|
||||
protected void setRequesterInfo(ALookupRequest lookup, HttpServerExchange exchange) {
|
||||
InetSocketAddress addr = (InetSocketAddress) exchange.getConnection().getPeerAddress();
|
||||
lookup.setRequester(addr.getAddress().getHostAddress());
|
||||
String xff = exchange.getRequestHeaders().getFirst("X-Forwarded-For");
|
||||
log.debug("XFF header: {}", xff);
|
||||
lookup.setRecursive(StringUtils.isBlank(xff));
|
||||
if (!lookup.isRecursive()) {
|
||||
lookup.setRecurseHosts(Arrays.asList(xff.split(",")));
|
||||
lookup.setRequester(lookup.getRecurseHosts().get(lookup.getRecurseHosts().size() - 1));
|
||||
}
|
||||
|
||||
lookup.setUserAgent(exchange.getRequestHeaders().getFirst("User-Agent"));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.matrix.crypto.KeyManager;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class RegularKeyIsValidHandler extends KeyIsValidHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/pubkey/isvalid";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(RegularKeyIsValidHandler.class);
|
||||
|
||||
private KeyManager mgr;
|
||||
|
||||
public RegularKeyIsValidHandler(KeyManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String pubKey = getQueryParameter(exchange, "public_key");
|
||||
log.info("Validating public key {}", pubKey);
|
||||
|
||||
// TODO do in manager
|
||||
boolean valid = StringUtils.equals(pubKey, mgr.getPublicKeyBase64(mgr.getCurrentIndex()));
|
||||
respondJson(exchange, valid ? validKey : invalidKey);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2017 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
public class RemoteIdentityAPIv1 {
|
||||
|
||||
public static final String BASE = "/_matrix/identity/remote/api/v1";
|
||||
public static final String SESSION_REQUEST_TOKEN = BASE + "/validate/requestToken";
|
||||
public static final String SESSION_CHECK = BASE + "/validate/check";
|
||||
|
||||
public static String getRequestToken(String id, String secret) {
|
||||
return SESSION_REQUEST_TOKEN + "?sid=" + id + "&client_secret=" + secret;
|
||||
}
|
||||
|
||||
public static String getSessionCheck(String id, String secret) {
|
||||
return SESSION_CHECK + "?sid=" + id + "&client_secret=" + secret;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.config.ViewConfig;
|
||||
import io.kamax.mxisd.exception.SessionNotValidatedException;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
|
||||
public class RemoteSessionCheckHandler extends BasicHttpHandler {
|
||||
|
||||
private SessionMananger mgr;
|
||||
private ViewConfig viewCfg;
|
||||
|
||||
public RemoteSessionCheckHandler(SessionMananger mgr, ViewConfig viewCfg) {
|
||||
this.mgr = mgr;
|
||||
this.viewCfg = viewCfg;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
String sid = getQueryParameter(exchange, "sid");
|
||||
String secret = getQueryParameter(exchange, "client_secret");
|
||||
|
||||
try {
|
||||
FileInputStream f = new FileInputStream(viewCfg.getSession().getRemote().getOnCheck().getSuccess());
|
||||
String viewData = IOUtils.toString(f, StandardCharsets.UTF_8);
|
||||
|
||||
mgr.validateRemote(sid, secret);
|
||||
|
||||
writeBodyAsUtf8(exchange, viewData);
|
||||
} catch (SessionNotValidatedException e) {
|
||||
FileInputStream f = new FileInputStream(viewCfg.getSession().getRemote().getOnCheck().getFailure());
|
||||
String viewData = IOUtils.toString(f, StandardCharsets.UTF_8);
|
||||
writeBodyAsUtf8(exchange, viewData);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.config.ViewConfig;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.kamax.mxisd.threepid.session.IThreePidSession;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
|
||||
public class RemoteSessionStartHandler extends BasicHttpHandler {
|
||||
|
||||
private SessionMananger mgr;
|
||||
private ViewConfig viewCfg;
|
||||
|
||||
public RemoteSessionStartHandler(SessionMananger mgr, ViewConfig viewCfg) {
|
||||
this.mgr = mgr;
|
||||
this.viewCfg = viewCfg;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) throws Exception {
|
||||
String sid = getQueryParameter(exchange, "sid");
|
||||
String secret = getQueryParameter(exchange, "client_secret");
|
||||
IThreePidSession session = mgr.createRemote(sid, secret);
|
||||
|
||||
FileInputStream f = new FileInputStream(viewCfg.getSession().getRemote().getOnRequest().getSuccess());
|
||||
String rawData = IOUtils.toString(f, StandardCharsets.UTF_8);
|
||||
String data = rawData.replace("${checkLink}", RemoteIdentityAPIv1.getSessionCheck(session.getId(), session.getSecret()));
|
||||
writeBodyAsUtf8(exchange, data);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.matrix.ThreePid;
|
||||
import io.kamax.matrix.ThreePidMedium;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.io.identity.RequestTokenResponse;
|
||||
import io.kamax.mxisd.http.io.identity.SessionEmailTokenRequestJson;
|
||||
import io.kamax.mxisd.http.io.identity.SessionPhoneTokenRequestJson;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.http.HttpStatus;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class SessionStartHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Medium = "medium";
|
||||
public static final String Path = IsAPIv1.Base + "/validate/{" + Medium + "}/requestToken";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SessionStartHandler.class);
|
||||
|
||||
private SessionMananger mgr;
|
||||
|
||||
public SessionStartHandler(SessionMananger mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String medium = getPathVariable(exchange, "medium");
|
||||
|
||||
if (ThreePidMedium.Email.is(medium)) {
|
||||
SessionEmailTokenRequestJson req = parseJsonTo(exchange, SessionEmailTokenRequestJson.class);
|
||||
ThreePid threepid = new ThreePid(req.getMedium(), req.getValue());
|
||||
|
||||
respondJson(exchange, new RequestTokenResponse(mgr.create(
|
||||
getRemoteHostAddress(exchange),
|
||||
threepid,
|
||||
req.getSecret(),
|
||||
req.getAttempt(),
|
||||
req.getNextLink())));
|
||||
} else if (ThreePidMedium.PhoneNumber.is(medium)) {
|
||||
SessionPhoneTokenRequestJson req = parseJsonTo(exchange, SessionPhoneTokenRequestJson.class);
|
||||
ThreePid threepid = new ThreePid(req.getMedium(), req.getValue());
|
||||
|
||||
String sessionId = mgr.create(
|
||||
getRemoteHostAddress(exchange),
|
||||
threepid,
|
||||
req.getSecret(),
|
||||
req.getAttempt(),
|
||||
req.getNextLink());
|
||||
|
||||
JsonObject res = new JsonObject();
|
||||
res.addProperty("sid", sessionId);
|
||||
res.addProperty(threepid.getMedium(), threepid.getAddress());
|
||||
respond(exchange, res);
|
||||
} else {
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.addProperty("errcode", "M_INVALID_3PID_TYPE");
|
||||
obj.addProperty("error", medium + " is not supported as a 3PID type");
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, obj);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.mxisd.exception.BadRequestException;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.invitation.InvitationManager;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.http.HttpStatus;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class SessionTpidBindHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/3pid/bind";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SessionTpidBindHandler.class);
|
||||
|
||||
private SessionMananger mgr;
|
||||
private InvitationManager invMgr;
|
||||
|
||||
public SessionTpidBindHandler(SessionMananger mgr, InvitationManager invMgr) {
|
||||
this.mgr = mgr;
|
||||
this.invMgr = invMgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String sid = getQueryParameter(exchange, "sid");
|
||||
String secret = getQueryParameter(exchange, "client_secret");
|
||||
String mxid = getQueryParameter(exchange, "mxid");
|
||||
|
||||
try {
|
||||
mgr.bind(sid, secret, mxid);
|
||||
respond(exchange, new JsonObject());
|
||||
} catch (BadRequestException e) {
|
||||
log.info("requested session was not validated");
|
||||
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.addProperty("errcode", "M_SESSION_NOT_VALIDATED");
|
||||
obj.addProperty("error", e.getMessage());
|
||||
respond(exchange, HttpStatus.SC_BAD_REQUEST, obj);
|
||||
} finally {
|
||||
// If a user registers, there is no standard login event. Instead, this is the only way to trigger
|
||||
// resolution at an appropriate time. Meh at synapse/Riot!
|
||||
invMgr.lookupMappingsForInvites();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.mxisd.exception.SessionNotValidatedException;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.lookup.ThreePidValidation;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
public class SessionTpidGetValidatedHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/3pid/getValidated3pid";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SessionTpidGetValidatedHandler.class);
|
||||
|
||||
private SessionMananger mgr;
|
||||
|
||||
public SessionTpidGetValidatedHandler(SessionMananger mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String sid = getQueryParameter(exchange, "sid");
|
||||
String secret = getQueryParameter(exchange, "client_secret");
|
||||
|
||||
try {
|
||||
ThreePidValidation pid = mgr.getValidated(sid, secret);
|
||||
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.addProperty("medium", pid.getMedium());
|
||||
obj.addProperty("address", pid.getAddress());
|
||||
obj.addProperty("validated_at", pid.getValidation().toEpochMilli());
|
||||
|
||||
respond(exchange, obj);
|
||||
} catch (SessionNotValidatedException e) {
|
||||
log.info("Session {} was requested but has not yet been validated", sid);
|
||||
throw e;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,124 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.mxisd.config.ServerConfig;
|
||||
import io.kamax.mxisd.config.ViewConfig;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.io.identity.SuccessStatusJson;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.session.SessionMananger;
|
||||
import io.kamax.mxisd.session.ValidationResult;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import io.undertow.util.HttpString;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URL;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
|
||||
public class SessionValidateHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/validate/{medium}/submitToken";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SessionValidateHandler.class);
|
||||
|
||||
private SessionMananger mgr;
|
||||
private ServerConfig srvCfg;
|
||||
private ViewConfig viewCfg;
|
||||
|
||||
public SessionValidateHandler(SessionMananger mgr, ServerConfig srvCfg, ViewConfig viewCfg) {
|
||||
this.mgr = mgr;
|
||||
this.srvCfg = srvCfg;
|
||||
this.viewCfg = viewCfg;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String medium = getQueryParameter(exchange, "medium");
|
||||
String sid = getQueryParameter(exchange, "sid");
|
||||
String secret = getQueryParameter(exchange, "client_secret");
|
||||
String token = getQueryParameter(exchange, "token");
|
||||
|
||||
boolean isHtmlRequest = false;
|
||||
for (String v : exchange.getRequestHeaders().get("Accept")) {
|
||||
if (StringUtils.startsWithIgnoreCase(v, "text/html")) {
|
||||
isHtmlRequest = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (isHtmlRequest) {
|
||||
handleHtmlRequest(exchange, medium, sid, secret, token);
|
||||
} else {
|
||||
handleJsonRequest(exchange, medium, sid, secret, token);
|
||||
}
|
||||
}
|
||||
|
||||
public void handleHtmlRequest(HttpServerExchange exchange, String medium, String sid, String secret, String token) {
|
||||
log.info("Validating session {} for medium {}", sid, medium);
|
||||
ValidationResult r = mgr.validate(sid, secret, token);
|
||||
log.info("Session {} was validated", sid);
|
||||
if (r.getNextUrl().isPresent()) {
|
||||
String url = r.getNextUrl().get();
|
||||
try {
|
||||
url = new URL(url).toString();
|
||||
} catch (MalformedURLException e) {
|
||||
log.info("Session next URL {} is not a valid one, will prepend public URL {}", url, srvCfg.getPublicUrl());
|
||||
url = srvCfg.getPublicUrl() + r.getNextUrl().get();
|
||||
}
|
||||
log.info("Session {} validation: next URL is present, redirecting to {}", sid, url);
|
||||
exchange.setStatusCode(302);
|
||||
exchange.getResponseHeaders().add(HttpString.tryFromString("Location"), url);
|
||||
} else {
|
||||
try {
|
||||
if (r.isCanRemote()) {
|
||||
FileInputStream f = new FileInputStream(viewCfg.getSession().getLocalRemote().getOnTokenSubmit().getSuccess());
|
||||
String url = srvCfg.getPublicUrl() + RemoteIdentityAPIv1.getRequestToken(r.getSession().getId(), r.getSession().getSecret());
|
||||
String rawData = IOUtils.toString(f, StandardCharsets.UTF_8);
|
||||
String data = rawData.replace("${remoteSessionLink}", url);
|
||||
writeBodyAsUtf8(exchange, data);
|
||||
} else {
|
||||
FileInputStream f = new FileInputStream(viewCfg.getSession().getLocalRemote().getOnTokenSubmit().getSuccess());
|
||||
String data = IOUtils.toString(f, StandardCharsets.UTF_8);
|
||||
writeBodyAsUtf8(exchange, data);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void handleJsonRequest(HttpServerExchange exchange, String medium, String sid, String secret, String token) {
|
||||
log.info("Requested: {}", exchange.getRequestURL());
|
||||
|
||||
ValidationResult r = mgr.validate(sid, secret, token);
|
||||
log.info("Session {} was validated", sid);
|
||||
|
||||
respondJson(exchange, new SuccessStatusJson(true));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.matrix.crypto.SignatureManager;
|
||||
import io.kamax.matrix.event.EventKey;
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.matrix.json.MatrixJson;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.io.identity.SingeLookupReplyJson;
|
||||
import io.kamax.mxisd.lookup.SingleLookupReply;
|
||||
import io.kamax.mxisd.lookup.SingleLookupRequest;
|
||||
import io.kamax.mxisd.lookup.strategy.LookupStrategy;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public class SingleLookupHandler extends LookupHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/lookup";
|
||||
|
||||
private transient final Logger log = LoggerFactory.getLogger(SingleLookupHandler.class);
|
||||
|
||||
private LookupStrategy strategy;
|
||||
private SignatureManager signMgr;
|
||||
|
||||
public SingleLookupHandler(LookupStrategy strategy, SignatureManager signMgr) {
|
||||
this.strategy = strategy;
|
||||
this.signMgr = signMgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String medium = getQueryParameter(exchange, "medium");
|
||||
String address = getQueryParameter(exchange, "address");
|
||||
|
||||
SingleLookupRequest lookupRequest = new SingleLookupRequest();
|
||||
setRequesterInfo(lookupRequest, exchange);
|
||||
lookupRequest.setType(medium);
|
||||
lookupRequest.setThreePid(address);
|
||||
|
||||
log.info("Got single lookup request from {} with client {} - Is recursive? {}",
|
||||
lookupRequest.getRequester(), lookupRequest.getUserAgent(), lookupRequest.isRecursive());
|
||||
|
||||
Optional<SingleLookupReply> lookupOpt = strategy.find(lookupRequest);
|
||||
if (!lookupOpt.isPresent()) {
|
||||
log.info("No mapping was found, return empty JSON object");
|
||||
respondJson(exchange, "{}");
|
||||
} else {
|
||||
SingleLookupReply lookup = lookupOpt.get();
|
||||
|
||||
// FIXME signing should be done in the business model, not in the controller
|
||||
JsonObject obj = GsonUtil.makeObj(new SingeLookupReplyJson(lookup));
|
||||
obj.add(EventKey.Signatures.get(), signMgr.signMessageGson(MatrixJson.encodeCanonical(obj)));
|
||||
|
||||
respondJson(exchange, obj);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.identity.v1;
|
||||
|
||||
import io.kamax.matrix.MatrixID;
|
||||
import io.kamax.matrix.crypto.KeyManager;
|
||||
import io.kamax.mxisd.config.ServerConfig;
|
||||
import io.kamax.mxisd.http.IsAPIv1;
|
||||
import io.kamax.mxisd.http.io.identity.ThreePidInviteReplyIO;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.kamax.mxisd.invitation.IThreePidInvite;
|
||||
import io.kamax.mxisd.invitation.IThreePidInviteReply;
|
||||
import io.kamax.mxisd.invitation.InvitationManager;
|
||||
import io.kamax.mxisd.invitation.ThreePidInvite;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
import java.util.Deque;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
public class StoreInviteHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = IsAPIv1.Base + "/store-invite";
|
||||
|
||||
private ServerConfig cfg;
|
||||
private InvitationManager invMgr;
|
||||
private KeyManager keyMgr;
|
||||
|
||||
public StoreInviteHandler(ServerConfig cfg, InvitationManager invMgr, KeyManager keyMgr) {
|
||||
this.cfg = cfg;
|
||||
this.invMgr = invMgr;
|
||||
this.keyMgr = keyMgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
Map<String, String> parameters = new HashMap<>();
|
||||
|
||||
for (Map.Entry<String, Deque<String>> entry : exchange.getQueryParameters().entrySet()) {
|
||||
if (Objects.nonNull(entry.getValue().peekFirst())) {
|
||||
parameters.put(entry.getKey(), entry.getValue().peekFirst());
|
||||
}
|
||||
}
|
||||
|
||||
// TODO test with missing parameters to see behaviour
|
||||
String sender = parameters.get("sender");
|
||||
String medium = parameters.get("medium");
|
||||
String address = parameters.get("address");
|
||||
String roomId = parameters.get("room_id");
|
||||
|
||||
IThreePidInvite invite = new ThreePidInvite(MatrixID.asAcceptable(sender), medium, address, roomId, parameters);
|
||||
IThreePidInviteReply reply = invMgr.storeInvite(invite);
|
||||
|
||||
respondJson(exchange, new ThreePidInviteReplyIO(reply, keyMgr.getPublicKeyBase64(keyMgr.getCurrentIndex()), cfg.getPublicUrl()));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.profile.v1;
|
||||
|
||||
import io.kamax.matrix.MatrixID;
|
||||
import io.kamax.matrix._MatrixID;
|
||||
import io.kamax.matrix.json.GsonUtil;
|
||||
import io.kamax.mxisd.profile.ProfileManager;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Optional;
|
||||
|
||||
public class InternalProfileHandler extends ProfileHandler {
|
||||
|
||||
public static final String Path = "/_matrix-internal/profile/v1/{" + UserID + "}";
|
||||
|
||||
public InternalProfileHandler(ProfileManager mgr) {
|
||||
super(mgr);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String userId = getQueryParameter(exchange, UserID);
|
||||
_MatrixID mxId = MatrixID.asAcceptable(userId);
|
||||
URI target = URI.create(exchange.getRequestURI());
|
||||
Optional<String> accessTokenOpt = findAccessToken(exchange);
|
||||
|
||||
HttpGet reqOut = new HttpGet(target);
|
||||
accessTokenOpt.ifPresent(accessToken -> reqOut.addHeader(headerName, headerValuePrefix + accessToken));
|
||||
|
||||
respond(exchange, GsonUtil.makeObj("roles", GsonUtil.asArray(mgr.getRoles(mxId))));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.profile.v1;
|
||||
|
||||
import io.kamax.matrix.MatrixID;
|
||||
import io.kamax.matrix._MatrixID;
|
||||
import io.kamax.mxisd.http.undertow.handler.HomeserverProxyHandler;
|
||||
import io.kamax.mxisd.profile.ProfileManager;
|
||||
import io.kamax.mxisd.proxy.Response;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Optional;
|
||||
|
||||
public class ProfileHandler extends HomeserverProxyHandler {
|
||||
|
||||
public static final String UserID = "userId";
|
||||
public static final String Path = "/_matrix/client/r0/profile/{" + UserID + "}";
|
||||
|
||||
protected ProfileManager mgr;
|
||||
|
||||
public ProfileHandler(ProfileManager mgr) {
|
||||
this.mgr = mgr;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
String userId = getQueryParameter(exchange, UserID);
|
||||
_MatrixID mxId = MatrixID.asAcceptable(userId);
|
||||
URI target = URI.create(exchange.getRequestURL());
|
||||
Optional<String> accessTokenOpt = findAccessToken(exchange);
|
||||
|
||||
HttpGet reqOut = new HttpGet(target);
|
||||
accessTokenOpt.ifPresent(accessToken -> reqOut.addHeader(headerName, headerValuePrefix + accessToken));
|
||||
|
||||
Response res = mgr.enhance(mxId, reqOut);
|
||||
respond(exchange, res);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
/*
|
||||
* mxisd - Matrix Identity Server Daemon
|
||||
* Copyright (C) 2018 Kamax Sarl
|
||||
*
|
||||
* https://www.kamax.io/
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
package io.kamax.mxisd.http.undertow.handler.status;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import io.kamax.mxisd.http.undertow.handler.BasicHttpHandler;
|
||||
import io.undertow.server.HttpServerExchange;
|
||||
|
||||
public class StatusHandler extends BasicHttpHandler {
|
||||
|
||||
public static final String Path = "/_matrix/identity/status";
|
||||
|
||||
@Override
|
||||
public void handleRequest(HttpServerExchange exchange) {
|
||||
// TODO link to backend
|
||||
JsonObject status = new JsonObject();
|
||||
status.addProperty("health", "OK");
|
||||
|
||||
JsonObject obj = new JsonObject();
|
||||
obj.add("status", status);
|
||||
|
||||
respond(exchange, obj);
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user