This commit is contained in:
thosakwe 2017-01-20 17:40:48 -05:00
parent 929e7bbac6
commit 4c04e1193c
4 changed files with 99 additions and 76 deletions

View file

@ -1,6 +1,6 @@
# angel_framework
[![pub 1.0.0-dev.48](https://img.shields.io/badge/pub-1.0.0--dev.48-red.svg)](https://pub.dartlang.org/packages/angel_framework)
[![pub 1.0.0-dev.49](https://img.shields.io/badge/pub-1.0.0--dev.49-red.svg)](https://pub.dartlang.org/packages/angel_framework)
[![build status](https://travis-ci.org/angel-dart/framework.svg)](https://travis-ci.org/angel-dart/framework)
Core libraries for the Angel Framework.

View file

@ -41,6 +41,16 @@ class HookedService extends Service {
if (inner.app != null) this.app = inner.app;
}
RequestContext _getRequest(Map params) {
if (params == null) return null;
return params['__requestctx'];
}
ResponseContext _getResponse(Map params) {
if (params == null) return null;
return params['__responsectx'];
}
Map _stripReq(Map params) {
if (params == null)
return params;
@ -192,21 +202,21 @@ class HookedService extends Service {
Future<List> index([Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeIndexed._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.INDEXED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.INDEXED,
params: params));
if (before._canceled) {
HookedServiceEvent after = await beforeIndexed._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.INDEXED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.INDEXED,
params: params, result: before.result));
return after.result;
}
List result = await inner.index(params);
HookedServiceEvent after = await afterIndexed._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.INDEXED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.INDEXED,
params: params, result: result));
return after.result;
}
@ -215,22 +225,22 @@ class HookedService extends Service {
Future read(id, [Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeRead._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.READ,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.READ,
id: id, params: params));
if (before._canceled) {
HookedServiceEvent after = await afterRead._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.READ,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.READ,
id: id, params: params, result: before.result));
return after.result;
}
var result = await inner.read(id, params);
HookedServiceEvent after = await afterRead._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.READ,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.READ,
id: id, params: params, result: result));
return after.result;
}
@ -239,22 +249,22 @@ class HookedService extends Service {
Future create(data, [Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeCreated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.CREATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.CREATED,
data: data, params: params));
if (before._canceled) {
HookedServiceEvent after = await afterCreated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.CREATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.CREATED,
data: data, params: params, result: before.result));
return after.result;
}
var result = await inner.create(data, params);
HookedServiceEvent after = await afterCreated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.CREATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.CREATED,
data: data, params: params, result: result));
return after.result;
}
@ -263,22 +273,22 @@ class HookedService extends Service {
Future modify(id, data, [Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeModified._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.MODIFIED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.MODIFIED,
id: id, data: data, params: params));
if (before._canceled) {
HookedServiceEvent after = await afterModified._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.MODIFIED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.MODIFIED,
id: id, data: data, params: params, result: before.result));
return after.result;
}
var result = await inner.modify(id, data, params);
HookedServiceEvent after = await afterModified._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.MODIFIED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.MODIFIED,
id: id, data: data, params: params, result: result));
return after.result;
}
@ -287,22 +297,22 @@ class HookedService extends Service {
Future update(id, data, [Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeUpdated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.UPDATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.UPDATED,
id: id, data: data, params: params));
if (before._canceled) {
HookedServiceEvent after = await afterUpdated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.UPDATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.UPDATED,
id: id, data: data, params: params, result: before.result));
return after.result;
}
var result = await inner.update(id, data, params);
HookedServiceEvent after = await afterUpdated._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.UPDATED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.UPDATED,
id: id, data: data, params: params, result: result));
return after.result;
}
@ -311,29 +321,30 @@ class HookedService extends Service {
Future remove(id, [Map _params]) async {
var params = _stripReq(_params);
HookedServiceEvent before = await beforeRemoved._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.REMOVED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.REMOVED,
id: id, params: params));
if (before._canceled) {
HookedServiceEvent after = await afterRemoved._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.REMOVED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.REMOVED,
id: id, params: params, result: before.result));
return after.result;
}
var result = await inner.remove(id, params);
HookedServiceEvent after = await afterRemoved._emit(
new HookedServiceEvent._base(_params['__requestctx'],
params['__responsectx'], inner, HookedServiceEvent.REMOVED,
new HookedServiceEvent._base(_getRequest(_params),
_getResponse(_params), inner, HookedServiceEvent.REMOVED,
id: id, params: params, result: result));
return after.result;
}
/// Fires an `after` event. This will not be propagated to clients,
/// but will be broadcasted to WebSockets, etc.
Future<HookedServiceEvent> fire(String eventName, result, [HookedServiceEventListener callback]) async {
Future<HookedServiceEvent> fire(String eventName, result,
[HookedServiceEventListener callback]) async {
HookedServiceEventDispatcher dispatcher;
switch (eventName) {

View file

@ -124,7 +124,7 @@ class Angel extends AngelBase {
///
/// Returns false on failure; otherwise, returns the HttpServer.
Future<HttpServer> startServer([InternetAddress address, int port]) async {
final host = address ?? InternetAddress.LOOPBACK_IP_V4;
var host = address ?? InternetAddress.LOOPBACK_IP_V4;
this.httpServer = await _serverGenerator(host, port ?? 0);
preprocessRoutes();
return httpServer..listen(handleRequest);
@ -188,38 +188,44 @@ class Angel extends AngelBase {
return false;
}
Future<RequestContext> createRequestContext(HttpRequest request) {
_beforeProcessed.add(request);
return RequestContext.from(request, this);
}
Future<ResponseContext> createResponseContext(HttpResponse response) async =>
new ResponseContext(response, this);
/// Handles a single request.
Future handleRequest(HttpRequest request) async {
try {
_beforeProcessed.add(request);
final req = await RequestContext.from(request, this);
final res = new ResponseContext(request.response, this);
var req = await createRequestContext(request);
var res = await createResponseContext(request.response);
String requestedUrl = request.uri.path.replaceAll(_straySlashes, '');
if (requestedUrl.isEmpty) requestedUrl = '/';
final resolved =
var resolved =
resolveAll(requestedUrl, requestedUrl, method: request.method);
for (final result in resolved) req.params.addAll(result.allParams);
for (var result in resolved) req.params.addAll(result.allParams);
if (resolved.isNotEmpty) {
final route = resolved.first.route;
var route = resolved.first.route;
req.inject(Match, route.match(requestedUrl));
}
final m = new MiddlewarePipeline(resolved);
var m = new MiddlewarePipeline(resolved);
req.inject(MiddlewarePipeline, m);
final pipeline = []..addAll(before)..addAll(m.handlers)..addAll(after);
var pipeline = []..addAll(before)..addAll(m.handlers)..addAll(after);
_printDebug('Handler sequence on $requestedUrl: $pipeline');
for (final handler in pipeline) {
for (var handler in pipeline) {
try {
_printDebug('Executing handler: $handler');
final result = await executeHandler(handler, req, res);
var result = await executeHandler(handler, req, res);
_printDebug('Result: $result');
if (!result) {
@ -262,27 +268,7 @@ class Angel extends AngelBase {
}
try {
_afterProcessed.add(request);
if (!res.willCloseItself) {
for (var finalizer in responseFinalizers) {
await finalizer(req, res);
}
for (var key in res.headers.keys) {
request.response.headers.add(key, res.headers[key]);
}
request.response.headers
..chunkedTransferEncoding = res.chunked ?? true
..set(HttpHeaders.CONTENT_LENGTH, res.buffer.length);
request.response
..statusCode = res.statusCode
..cookies.addAll(res.cookies)
..add(res.buffer.takeBytes());
await request.response.close();
}
await sendRequest(request, req, res);
} catch (e, st) {
_fatalErrorStream
.add(new AngelFatalError(request: request, error: e, stack: st));
@ -339,6 +325,32 @@ class Angel extends AngelBase {
// return await closureMirror.apply(args).reflectee;
}
/// Sends a response.
Future sendRequest(
HttpRequest request, RequestContext req, ResponseContext res) async {
_afterProcessed.add(request);
if (!res.willCloseItself) {
for (var finalizer in responseFinalizers) {
await finalizer(req, res);
}
for (var key in res.headers.keys) {
request.response.headers.add(key, res.headers[key]);
}
request.response.headers
..chunkedTransferEncoding = res.chunked ?? true
..set(HttpHeaders.CONTENT_LENGTH, res.buffer.length);
request.response
..statusCode = res.statusCode
..cookies.addAll(res.cookies)
..add(res.buffer.takeBytes());
await request.response.close();
}
}
/// Applies an [AngelConfigurer] to this instance.
Future configure(AngelConfigurer configurer) async {
await configurer(this);
@ -366,7 +378,7 @@ class Angel extends AngelBase {
@override
use(Pattern path, Routable routable,
{bool hooked: true, String namespace: null}) {
final head = path.toString().replaceAll(_straySlashes, '');
var head = path.toString().replaceAll(_straySlashes, '');
if (routable is Angel) {
_children.add(routable.._parent = this);
@ -396,12 +408,12 @@ class Angel extends AngelBase {
}
routable.controllers.forEach((k, v) {
final tail = k.toString().replaceAll(_straySlashes, '');
var tail = k.toString().replaceAll(_straySlashes, '');
controllers['$head/$tail'.replaceAll(_straySlashes, '')] = v;
});
routable.services.forEach((k, v) {
final tail = k.toString().replaceAll(_straySlashes, '');
var tail = k.toString().replaceAll(_straySlashes, '');
services['$head/$tail'.replaceAll(_straySlashes, '')] = v;
});
}
@ -434,7 +446,7 @@ class Angel extends AngelBase {
/// the server.
factory Angel.secure(String certificateChainPath, String serverKeyPath,
{bool debug: false, String password}) {
final app = new Angel(debug: debug == true);
var app = new Angel(debug: debug == true);
app._serverGenerator = (InternetAddress address, int port) async {
var certificateChain =

View file

@ -1,5 +1,5 @@
name: angel_framework
version: 1.0.0-dev.48
version: 1.0.0-dev.49
description: Core libraries for the Angel framework.
author: Tobe O <thosakwe@gmail.com>
homepage: https://github.com/angel-dart/angel_framework