-
Notifications
You must be signed in to change notification settings - Fork 27
/
WebServer.swift
75 lines (61 loc) · 3.42 KB
/
WebServer.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
import Foundation
import GCDWebServers
class WebServer {
static let WebServerSharedInstance = WebServer()
class var sharedInstance: WebServer {
return WebServerSharedInstance
}
let server: GCDWebServer = GCDWebServer()
var base: String {
return "http://localhost:\(server.port)"
}
func start() throws -> Bool{
if !server.running {
// Cliqz: changed the webserver port so as not to conflict with Firefox one
try server.startWithOptions([GCDWebServerOption_Port: 6572, GCDWebServerOption_BindToLocalhost: true, GCDWebServerOption_AutomaticallySuspendInBackground: true])
}
return server.running
}
/// Convenience method to register a dynamic handler. Will be mounted at $base/$module/$resource
func registerHandlerForMethod(method: String, module: String, resource: String, handler: (request: GCDWebServerRequest!) -> GCDWebServerResponse!) {
// Prevent serving content if the requested host isn't a whitelisted local host.
let wrappedHandler = {(request: GCDWebServerRequest!) -> GCDWebServerResponse! in
guard request.URL.isLocal else {
return GCDWebServerResponse(statusCode: 403)
}
return handler(request: request)
}
server.addHandlerForMethod(method, path: "/\(module)/\(resource)", requestClass: GCDWebServerRequest.self, processBlock: wrappedHandler)
}
/// Convenience method to register a resource in the main bundle. Will be mounted at $base/$module/$resource
func registerMainBundleResource(resource: String, module: String) {
if let path = NSBundle.mainBundle().pathForResource(resource, ofType: nil) {
server.addGETHandlerForPath("/\(module)/\(resource)", filePath: path, isAttachment: false, cacheAge: UInt.max, allowRangeRequests: true)
}
}
/// Convenience method to register all resources in the main bundle of a specific type. Will be mounted at $base/$module/$resource
func registerMainBundleResourcesOfType(type: String, module: String) {
for path: NSString in NSBundle.pathsForResourcesOfType(type, inDirectory: NSBundle.mainBundle().bundlePath) {
let resource = path.lastPathComponent
server.addGETHandlerForPath("/\(module)/\(resource)", filePath: path as String, isAttachment: false, cacheAge: UInt.max, allowRangeRequests: true)
}
}
/// Return a full url, as a string, for a resource in a module. No check is done to find out if the resource actually exist.
func URLForResource(resource: String, module: String) -> String {
return "\(base)/\(module)/\(resource)"
}
/// Return a full url, as an NSURL, for a resource in a module. No check is done to find out if the resource actually exist.
func URLForResource(resource: String, module: String) -> NSURL {
return NSURL(string: "\(base)/\(module)/\(resource)")!
}
func updateLocalURL(url: NSURL) -> NSURL? {
let components = NSURLComponents(URL: url, resolvingAgainstBaseURL: false)
if components?.host == "localhost" && components?.scheme == "http" {
components?.port = WebServer.sharedInstance.server.port
}
return components?.URL
}
}