diff --git a/src/github.com/matrix-org/dendrite/cmd/dendrite-monolith-server/main.go b/src/github.com/matrix-org/dendrite/cmd/dendrite-monolith-server/main.go
index 3b5975763..ea71fed98 100644
--- a/src/github.com/matrix-org/dendrite/cmd/dendrite-monolith-server/main.go
+++ b/src/github.com/matrix-org/dendrite/cmd/dendrite-monolith-server/main.go
@@ -330,7 +330,7 @@ func (m *monolith) setupAPIs() {
 
 	syncapi_routing.Setup(m.api, syncapi_sync.NewRequestPool(
 		m.syncAPIDB, m.syncAPINotifier, m.accountDB,
-	), m.deviceDB)
+	), m.syncAPIDB, m.deviceDB)
 
 	federationapi_routing.Setup(
 		m.api, *m.cfg, m.queryAPI, m.roomServerProducer, m.keyRing, m.federation,
diff --git a/src/github.com/matrix-org/dendrite/cmd/dendrite-sync-api-server/main.go b/src/github.com/matrix-org/dendrite/cmd/dendrite-sync-api-server/main.go
index fb81b0e3d..e7f83a60d 100644
--- a/src/github.com/matrix-org/dendrite/cmd/dendrite-sync-api-server/main.go
+++ b/src/github.com/matrix-org/dendrite/cmd/dendrite-sync-api-server/main.go
@@ -104,7 +104,7 @@ func main() {
 	log.Info("Starting sync server on ", cfg.Listen.SyncAPI)
 
 	api := mux.NewRouter()
-	routing.Setup(api, sync.NewRequestPool(db, n, adb), deviceDB)
+	routing.Setup(api, sync.NewRequestPool(db, n, adb), db, deviceDB)
 	common.SetupHTTPAPI(http.DefaultServeMux, api)
 
 	log.Fatal(http.ListenAndServe(string(cfg.Listen.SyncAPI), nil))
diff --git a/src/github.com/matrix-org/dendrite/syncapi/routing/routing.go b/src/github.com/matrix-org/dendrite/syncapi/routing/routing.go
index 15ca267a0..6cdbe992a 100644
--- a/src/github.com/matrix-org/dendrite/syncapi/routing/routing.go
+++ b/src/github.com/matrix-org/dendrite/syncapi/routing/routing.go
@@ -21,6 +21,7 @@ import (
 	"github.com/matrix-org/dendrite/clientapi/auth/authtypes"
 	"github.com/matrix-org/dendrite/clientapi/auth/storage/devices"
 	"github.com/matrix-org/dendrite/common"
+	"github.com/matrix-org/dendrite/syncapi/storage"
 	"github.com/matrix-org/dendrite/syncapi/sync"
 	"github.com/matrix-org/util"
 )
@@ -28,7 +29,7 @@ import (
 const pathPrefixR0 = "/_matrix/client/r0"
 
 // Setup configures the given mux with sync-server listeners
-func Setup(apiMux *mux.Router, srp *sync.RequestPool, deviceDB *devices.Database) {
+func Setup(apiMux *mux.Router, srp *sync.RequestPool, syncDB *storage.SyncServerDatabase, deviceDB *devices.Database) {
 	r0mux := apiMux.PathPrefix(pathPrefixR0).Subrouter()
 
 	r0mux.Handle("/sync", common.MakeAuthAPI("sync", deviceDB, func(req *http.Request, device *authtypes.Device) util.JSONResponse {
@@ -37,16 +38,16 @@ func Setup(apiMux *mux.Router, srp *sync.RequestPool, deviceDB *devices.Database
 
 	r0mux.Handle("/rooms/{roomID}/state", common.MakeAuthAPI("room_state", deviceDB, func(req *http.Request, device *authtypes.Device) util.JSONResponse {
 		vars := mux.Vars(req)
-		return srp.OnIncomingStateRequest(req, vars["roomID"])
+		return OnIncomingStateRequest(req, syncDB, vars["roomID"])
 	})).Methods("GET")
 
 	r0mux.Handle("/rooms/{roomID}/state/{type}", common.MakeAuthAPI("room_state", deviceDB, func(req *http.Request, device *authtypes.Device) util.JSONResponse {
 		vars := mux.Vars(req)
-		return srp.OnIncomingStateTypeRequest(req, vars["roomID"], vars["type"], "")
+		return OnIncomingStateTypeRequest(req, syncDB, vars["roomID"], vars["type"], "")
 	})).Methods("GET")
 
 	r0mux.Handle("/rooms/{roomID}/state/{type}/{stateKey}", common.MakeAuthAPI("room_state", deviceDB, func(req *http.Request, device *authtypes.Device) util.JSONResponse {
 		vars := mux.Vars(req)
-		return srp.OnIncomingStateTypeRequest(req, vars["roomID"], vars["type"], vars["stateKey"])
+		return OnIncomingStateTypeRequest(req, syncDB, vars["roomID"], vars["type"], vars["stateKey"])
 	})).Methods("GET")
 }
diff --git a/src/github.com/matrix-org/dendrite/syncapi/routing/state.go b/src/github.com/matrix-org/dendrite/syncapi/routing/state.go
new file mode 100644
index 000000000..6c825fce8
--- /dev/null
+++ b/src/github.com/matrix-org/dendrite/syncapi/routing/state.go
@@ -0,0 +1,118 @@
+// 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 routing
+
+import (
+	"encoding/json"
+	"net/http"
+
+	"github.com/matrix-org/dendrite/clientapi/httputil"
+	"github.com/matrix-org/dendrite/clientapi/jsonerror"
+	"github.com/matrix-org/dendrite/syncapi/storage"
+	"github.com/matrix-org/dendrite/syncapi/types"
+	"github.com/matrix-org/gomatrixserverlib"
+	"github.com/matrix-org/util"
+	log "github.com/sirupsen/logrus"
+)
+
+type stateEventInStateResp struct {
+	gomatrixserverlib.ClientEvent
+	PrevContent   json.RawMessage `json:"prev_content,omitempty"`
+	ReplacesState string          `json:"replaces_state,omitempty"`
+}
+
+// OnIncomingStateRequest is called when a client makes a /rooms/{roomID}/state
+// request. It will fetch all the state events from the specified room and will
+// append the necessary keys to them if applicable before returning them.
+// Returns an error if something went wrong in the process.
+// TODO: Check if the user is in the room. If not, check if the room's history
+// is publicly visible. Current behaviour is returning an empty array if the
+// user cannot see the room's history.
+func OnIncomingStateRequest(req *http.Request, db *storage.SyncServerDatabase, roomID string) util.JSONResponse {
+	// TODO(#287): Auth request and handle the case where the user has left (where
+	// we should return the state at the poin they left)
+
+	stateEvents, err := db.GetStateEventsForRoom(req.Context(), roomID)
+	if err != nil {
+		return httputil.LogThenError(req, err)
+	}
+
+	resp := []stateEventInStateResp{}
+	// Fill the prev_content and replaces_state keys if necessary
+	for _, event := range stateEvents {
+		stateEvent := stateEventInStateResp{
+			ClientEvent: gomatrixserverlib.ToClientEvent(event, gomatrixserverlib.FormatAll),
+		}
+		var prevEventRef types.PrevEventRef
+		if len(event.Unsigned()) > 0 {
+			if err := json.Unmarshal(event.Unsigned(), &prevEventRef); err != nil {
+				return httputil.LogThenError(req, err)
+			}
+			// Fills the previous state event ID if the state event replaces another
+			// state event
+			if len(prevEventRef.ReplacesState) > 0 {
+				stateEvent.ReplacesState = prevEventRef.ReplacesState
+			}
+			// Fill the previous event if the state event references a previous event
+			if prevEventRef.PrevContent != nil {
+				stateEvent.PrevContent = prevEventRef.PrevContent
+			}
+		}
+
+		resp = append(resp, stateEvent)
+	}
+
+	return util.JSONResponse{
+		Code: 200,
+		JSON: resp,
+	}
+}
+
+// OnIncomingStateTypeRequest is called when a client makes a
+// /rooms/{roomID}/state/{type}/{statekey} request. It will look in current
+// state to see if there is an event with that type and state key, if there
+// is then (by default) we return the content, otherwise a 404.
+func OnIncomingStateTypeRequest(req *http.Request, db *storage.SyncServerDatabase, roomID string, evType, stateKey string) util.JSONResponse {
+	// TODO(#287): Auth request and handle the case where the user has left (where
+	// we should return the state at the poin they left)
+
+	logger := util.GetLogger(req.Context())
+	logger.WithFields(log.Fields{
+		"roomID":   roomID,
+		"evType":   evType,
+		"stateKey": stateKey,
+	}).Info("Fetching state")
+
+	event, err := db.GetStateEvent(req.Context(), roomID, evType, stateKey)
+	if err != nil {
+		return httputil.LogThenError(req, err)
+	}
+
+	if event == nil {
+		return util.JSONResponse{
+			Code: 404,
+			JSON: jsonerror.NotFound("cannot find state"),
+		}
+	}
+
+	stateEvent := stateEventInStateResp{
+		ClientEvent: gomatrixserverlib.ToClientEvent(*event, gomatrixserverlib.FormatAll),
+	}
+
+	return util.JSONResponse{
+		Code: 200,
+		JSON: stateEvent.Content,
+	}
+}
diff --git a/src/github.com/matrix-org/dendrite/syncapi/sync/requestpool.go b/src/github.com/matrix-org/dendrite/syncapi/sync/requestpool.go
index ebfb140d1..3b6775618 100644
--- a/src/github.com/matrix-org/dendrite/syncapi/sync/requestpool.go
+++ b/src/github.com/matrix-org/dendrite/syncapi/sync/requestpool.go
@@ -15,7 +15,6 @@
 package sync
 
 import (
-	"encoding/json"
 	"net/http"
 	"time"
 
@@ -120,96 +119,6 @@ func (rp *RequestPool) OnIncomingSyncRequest(req *http.Request, device *authtype
 	}
 }
 
-type stateEventInStateResp struct {
-	gomatrixserverlib.ClientEvent
-	PrevContent   json.RawMessage `json:"prev_content,omitempty"`
-	ReplacesState string          `json:"replaces_state,omitempty"`
-}
-
-// OnIncomingStateRequest is called when a client makes a /rooms/{roomID}/state
-// request. It will fetch all the state events from the specified room and will
-// append the necessary keys to them if applicable before returning them.
-// Returns an error if something went wrong in the process.
-// TODO: Check if the user is in the room. If not, check if the room's history
-// is publicly visible. Current behaviour is returning an empty array if the
-// user cannot see the room's history.
-func (rp *RequestPool) OnIncomingStateRequest(req *http.Request, roomID string) util.JSONResponse {
-	// TODO(#287): Auth request and handle the case where the user has left (where
-	// we should return the state at the poin they left)
-
-	stateEvents, err := rp.db.GetStateEventsForRoom(req.Context(), roomID)
-	if err != nil {
-		return httputil.LogThenError(req, err)
-	}
-
-	resp := []stateEventInStateResp{}
-	// Fill the prev_content and replaces_state keys if necessary
-	for _, event := range stateEvents {
-		stateEvent := stateEventInStateResp{
-			ClientEvent: gomatrixserverlib.ToClientEvent(event, gomatrixserverlib.FormatAll),
-		}
-		var prevEventRef types.PrevEventRef
-		if len(event.Unsigned()) > 0 {
-			if err := json.Unmarshal(event.Unsigned(), &prevEventRef); err != nil {
-				return httputil.LogThenError(req, err)
-			}
-			// Fills the previous state event ID if the state event replaces another
-			// state event
-			if len(prevEventRef.ReplacesState) > 0 {
-				stateEvent.ReplacesState = prevEventRef.ReplacesState
-			}
-			// Fill the previous event if the state event references a previous event
-			if prevEventRef.PrevContent != nil {
-				stateEvent.PrevContent = prevEventRef.PrevContent
-			}
-		}
-
-		resp = append(resp, stateEvent)
-	}
-
-	return util.JSONResponse{
-		Code: 200,
-		JSON: resp,
-	}
-}
-
-// OnIncomingStateTypeRequest is called when a client makes a
-// /rooms/{roomID}/state/{type}/{statekey} request. It will look in current
-// state to see if there is an event with that type and state key, if there
-// is then (by default) we return the content, otherwise a 404.
-func (rp *RequestPool) OnIncomingStateTypeRequest(req *http.Request, roomID string, evType, stateKey string) util.JSONResponse {
-	// TODO(#287): Auth request and handle the case where the user has left (where
-	// we should return the state at the poin they left)
-
-	logger := util.GetLogger(req.Context())
-	logger.WithFields(log.Fields{
-		"roomID":   roomID,
-		"evType":   evType,
-		"stateKey": stateKey,
-	}).Info("Fetching state")
-
-	event, err := rp.db.GetStateEvent(req.Context(), roomID, evType, stateKey)
-	if err != nil {
-		return httputil.LogThenError(req, err)
-	}
-
-	if event == nil {
-		return util.JSONResponse{
-			Code: 404,
-			JSON: jsonerror.NotFound("cannot find state"),
-		}
-	}
-
-	stateEvent := stateEventInStateResp{
-		ClientEvent: gomatrixserverlib.ToClientEvent(*event, gomatrixserverlib.FormatAll),
-	}
-
-	return util.JSONResponse{
-		Code: 200,
-		JSON: stateEvent.Content,
-	}
-}
-
 func (rp *RequestPool) currentSyncForUser(req syncRequest, currentPos types.StreamPosition) (res *types.Response, err error) {
 	// TODO: handle ignored users
 	if req.since == types.StreamPosition(0) {