Implement public rooms directory

This commit is contained in:
Brendan Abolivier 2017-08-16 15:00:09 +01:00
parent 6ecefebcd1
commit 83f8effbed
No known key found for this signature in database
GPG key ID: 8EF1500759F70623
3 changed files with 114 additions and 0 deletions

View file

@ -0,0 +1,108 @@
// Copyright 2017 Vector Creations Ltd
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package directory
import (
"net/http"
"strconv"
"github.com/matrix-org/dendrite/clientapi/httputil"
"github.com/matrix-org/dendrite/clientapi/jsonerror"
"github.com/matrix-org/dendrite/publicroomsapi/storage"
"github.com/matrix-org/dendrite/publicroomsapi/types"
"github.com/matrix-org/util"
)
type publicRoomReq struct {
Since string `json:"since,omitempty"`
Limit int16 `json:"limit,omitempty"`
Filter string `json:"filter,omitempty"`
}
type publicRoomRes struct {
Chunk []types.PublicRoom `json:"chunk"`
NextBatch string `json:"next_batch,omitempty"`
PrevBatch string `json:"prev_batch,omitempty"`
Estimate int64 `json:"total_room_count_estimate,omitempty"`
}
// GetPublicRooms implements GET /publicRooms
func GetPublicRooms(
req *http.Request, publicRoomDatabase *storage.PublicRoomsServerDatabase,
) util.JSONResponse {
var limit int16
var offset int64
var request publicRoomReq
var response publicRoomRes
if fillErr := fillPublicRoomsReq(req, &request); fillErr != nil {
return *fillErr
}
limit = request.Limit
offset, err := strconv.ParseInt(request.Since, 10, 64)
// ParseInt returns 0 and an error when trying to parse an empty string
// In that case, we want to assign 0 so we ignore the error
if err != nil && len(request.Since) > 0 {
return httputil.LogThenError(req, err)
}
if response.Estimate, err = publicRoomDatabase.CountPublicRooms(); err != nil {
return httputil.LogThenError(req, err)
}
if offset > 0 {
response.PrevBatch = strconv.Itoa(int(offset) - 1)
}
if response.Estimate > int64(limit) {
response.NextBatch = strconv.Itoa(int(offset) + int(limit))
}
if response.Chunk, err = publicRoomDatabase.GetPublicRooms(offset, limit); err != nil {
return httputil.LogThenError(req, err)
}
return util.JSONResponse{
Code: 200,
JSON: response,
}
}
// fillPublicRoomsReq fills the Limit, Since and Filter attributes of a GET or POST request
// on /publicRooms by parsing the incoming HTTP request
func fillPublicRoomsReq(httpReq *http.Request, request *publicRoomReq) *util.JSONResponse {
if httpReq.Method == "GET" {
limit, err := strconv.Atoi(httpReq.FormValue("limit"))
// Atoi returns 0 and an error when trying to parse an empty string
// In that case, we want to assign 0 so we ignore the error
if err != nil && len(httpReq.FormValue("limit")) > 0 {
reqErr := httputil.LogThenError(httpReq, err)
return &reqErr
}
request.Limit = int16(limit)
request.Since = httpReq.FormValue("since")
return nil
} else if httpReq.Method == "POST" {
if reqErr := httputil.UnmarshalJSONRequest(httpReq, request); reqErr != nil {
return reqErr
}
return nil
}
return &util.JSONResponse{
Code: 405,
JSON: jsonerror.NotFound("Bad method"),
}
}

View file

@ -41,4 +41,9 @@ func Setup(apiMux *mux.Router, publicRoomsDB *storage.PublicRoomsServerDatabase)
return directory.SetVisibility(req, publicRoomsDB, vars["roomID"])
}),
).Methods("PUT", "OPTIONS")
r0mux.Handle("/publicRooms",
common.MakeAPI("public_rooms", func(req *http.Request) util.JSONResponse {
return directory.GetPublicRooms(req, publicRoomsDB)
}),
).Methods("GET", "POST", "OPTIONS")
}

View file

@ -31,6 +31,7 @@ var editableAttributes = []string{
"world_readable",
"guest_can_join",
"avatar_url",
"visibility",
}
const publicRoomsSchema = `