Merge pull request #102 from dukefirehawk/feature/v8

Feature/v8
This commit is contained in:
Thomas Hii 2023-06-09 00:52:09 +08:00 committed by GitHub
commit b83adcd51a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
190 changed files with 26550 additions and 2032 deletions

View file

@ -1,5 +1,6 @@
{ {
"image": "dart:3.0", "image": "dart:3.0",
"forwardPorts": [3000,5000],
"features": { "features": {
} }
} }

View file

@ -1,5 +1,57 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Updated: angel3_http_exception
* Updated: angel3_route
* Updated: angel3_model
* Updated: angel3_container
* Updated: angel3_container_generator
* Updated: angel3_mock_request
* Updated: angel3_framework
* Updated: angel3_auth
* Updated: angel3_configuration
* Updated: angel3_validate
* Updated: angel3_client
* Updated: angel3_websocket
* Updated: angel3_test
* Updated: jael3
* Updated: jael3_preprocessor
* Updated: jael3_language_server
* Updated: angel3_jael
* Updated: jael3_web
* Updated: angel3_production
* Updated: angel3_hot
* Updated: angel3_static
* Updated: angel3_serialize
* Updated: angel3_serialize_generator
* Updated: angel3_orm
* Updated: angel3_orm_generator
* Updated: angel3_migration
* Updated: angel3_migration_generator
* Updated: angel3_orm_postgresql
* Updated: angel3_orm_mysql
* Updated: angel3_orm_service
* Updated: angel3_orm_test
* Updated: angel3_orm_cache
* Updated: angel3_orm_cors
* Updated: angel3_mustache
* Updated: angel3_proxy
* Updated: angel3_redis
* Updated: angel3_jinja
* Updated: angel3_security
* Updated: angel3_user_agent
* Updated: angel3_seo
* Updated: angel3_sync
* Updated: angel3_sembast
* Updated: angel3_markdown
* Updated: angel3_auth_oauth2
* Updated: angel3_oauth2 (5 failed test cases)
* Updated: angel3_auth_twitter (issue: oauth1 don't support http 1.0.0)
* Updated: angel3_mongo (issue: mongo_dart don't support http 1.0.0)
* Updated: angel3_shelf (2 failed test cases)
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -8,7 +8,7 @@
[![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/LICENSE) [![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/LICENSE)
[![melos](https://img.shields.io/badge/maintained%20with-melos-f700ff.svg?style=flat-square)](https://github.com/invertase/melos) [![melos](https://img.shields.io/badge/maintained%20with-melos-f700ff.svg?style=flat-square)](https://github.com/invertase/melos)
**A polished, production-ready backend framework in Dart with NNBD support.** **A polished, production-ready backend framework in Dart.**
----- -----
@ -33,7 +33,15 @@ See all of the available [`packages`](https://angel3-docs.dukefirehawk.com/packa
## Important Notes ## Important Notes
Angel3 packages are published under `angel3_` prefix on pub.dev. These packages have passed all of their respective test suites before going live. The development work is ongoing in improving its features and performance for better development and deployment experience. Angel3 packages are published under `angel3_` prefix on pub.dev. These packages have passed all of their respective test suites before going live. The development work are currently focused on:
* Keeping the packages with `angel3_` prefix in sync with Dart SDK releases
* Remove and replace deprecated classes and methods while keeping backward compatible
* Refactor the code to use new language features
* Fix and resolve reported issues
* Performance tunning
* Improve on existing features, unit test, user guide and examples
* Add new features
The status of the project is as follows: The status of the project is as follows:
@ -58,8 +66,9 @@ For more details, checkout [Project Status](https://github.com/dukefirehawk/ange
## Release Notes ## Release Notes
### Release 7.0.0 (Current Release) ### Release 7.0.0 (Current)
* Updated all `angel3_` packages to 7.0.0
* Updated all `angel3_` packages to require dart >= 2.17.x * Updated all `angel3_` packages to require dart >= 2.17.x
* Updated dependencies to the latest libraries * Updated dependencies to the latest libraries
* Updated code generator to use `analyzer` 5.x.x * Updated code generator to use `analyzer` 5.x.x
@ -164,6 +173,29 @@ You can also view the [Angel3 API](http://www.dartdocs.org/documentation/angel_f
Interested in contributing to Angel3? See the contribution guide [here](CONTRIBUTING.md). Interested in contributing to Angel3? See the contribution guide [here](CONTRIBUTING.md).
### Development Setup
1. Fork `angel` repository
2. Clone the project to local and create a new branch
```bash
git clone https://github.com/<your_repo_name>/angel.git
git checkout -b feature/<your_branch_name>
```
3. Download and install [Dart 3](https://dart.dev/get-dart)
4. Install `melos` 3.0
```bash
dart pub global activate melos
```
5. Run `melos exec "dart pub upgrade"` to update all the packages
6. Make changes to the packages
## Donation & Support ## Donation & Support
If you like this project and interested in supporting its development, you can make a donation via [paypal](https://paypal.me/dukefirehawk?country.x=MY&locale.x=en_US) service. If you like this project and interested in supporting its development, you can make a donation via [paypal](https://paypal.me/dukefirehawk?country.x=MY&locale.x=en_US) service.

View file

@ -0,0 +1,44 @@
import 'dart:mirrors';
import 'package:example1/src/models.dart';
void main() {
final stopwatch = Stopwatch()..start();
var reflectedClass = reflect(Shape());
reflectedClass.invoke(#draw, []);
//reflectedClass.invoke(Symbol('draw'), []);
print('Reflection executed in ${stopwatch.elapsed.inMilliseconds} ms');
stopwatch.stop();
printAnnotationValue(String);
printAnnotationValue(Shape);
printAnnotationValue(Square);
}
class Shape {
void draw() => print("Draw Shape");
}
@Person('Will', 'Tom')
class Square {
void greetHii() {
print("Hii Welcome to flutter agency");
}
}
void printAnnotationValue(final Type clazz) {
final DeclarationMirror clazzDeclaration = reflectClass(clazz);
final ClassMirror someAnnotationMirror = reflectClass(Person);
final annotationInstsanceMirror =
clazzDeclaration.metadata.where((d) => d.type == someAnnotationMirror);
if (annotationInstsanceMirror.isEmpty) {
print('No annotated class found');
return;
}
final someAnnotationInstance =
(annotationInstsanceMirror.first.reflectee as Person);
print(someAnnotationInstance.firstName);
}

View file

@ -0,0 +1,5 @@
class Person {
final String firstName;
final String lastName;
const Person(this.firstName, this.lastName);
}

View file

@ -1,30 +0,0 @@
import 'package:angel3_container/angel3_container.dart';
import 'package:angel3_container_generator/angel3_container_generator.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
import 'example.reflectable.dart';
@Expose('/controller')
class MyController extends Controller {
@Expose('/')
a() => "Hello, world!";
}
void main() async {
initializeReflectable();
var reflector = const GeneratedReflector();
Container container = Container(reflector);
container.registerSingleton<MyController>(MyController());
var app = Angel(reflector: reflector);
var http = AngelHttp(app);
//await app.mountController<MyController>();
var server = await http.startServer('localhost', 3000);
print("Angel server listening at ${http.uri}");
}

View file

@ -1,300 +0,0 @@
// This file has been generated by the reflectable package.
// https://github.com/dart-lang/reflectable.
// @dart = 2.12
import 'dart:core';
import 'package:angel3_container_generator/angel3_container_generator.dart'
as prefix0;
import 'package:reflectable/capability.dart' as prefix1;
import 'package:reflectable/mirrors.dart' as prefix2;
// ignore_for_file: camel_case_types
// ignore_for_file: implementation_imports
// ignore_for_file: prefer_adjacent_string_concatenation
// ignore_for_file: prefer_collection_literals
// ignore_for_file: unnecessary_const
// ignore:unused_import
import 'package:reflectable/mirrors.dart' as m;
// ignore:unused_import
import 'package:reflectable/src/reflectable_builder_based.dart' as r;
// ignore:unused_import
import 'package:reflectable/reflectable.dart' as r show Reflectable;
final _data = <r.Reflectable, r.ReflectorData>{
const prefix0.ContainedReflectable(): r.ReflectorData(
<m.TypeMirror>[
r.NonGenericClassMirrorImpl(
r'ContainedReflectable',
r'.ContainedReflectable',
134217735,
0,
const prefix0.ContainedReflectable(),
const <int>[0],
const <int>[1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13],
const <int>[],
-1,
{},
{},
{r'': (bool b) => () => b ? prefix0.ContainedReflectable() : null},
0,
0,
const <int>[],
const <Object>[prefix0.contained],
null)
],
<m.DeclarationMirror>[
r.MethodMirrorImpl(r'', 128, 0, -1, 0, 0, const <int>[], const <int>[],
const prefix0.ContainedReflectable(), const []),
r.MethodMirrorImpl(r'==', 2097154, -1, -1, 1, 1, const <int>[],
const <int>[0], const prefix0.ContainedReflectable(), const []),
r.MethodMirrorImpl(r'toString', 2097154, -1, -1, 2, 2, const <int>[],
const <int>[], const prefix0.ContainedReflectable(), const []),
r.MethodMirrorImpl(
r'noSuchMethod',
524290,
-1,
-1,
-1,
-1,
const <int>[],
const <int>[1],
const prefix0.ContainedReflectable(),
const []),
r.MethodMirrorImpl(r'hashCode', 2097155, -1, -1, 3, 3, const <int>[],
const <int>[], const prefix0.ContainedReflectable(), const []),
r.MethodMirrorImpl(r'runtimeType', 2097155, -1, -1, 4, 4, const <int>[],
const <int>[], const prefix0.ContainedReflectable(), const []),
r.MethodMirrorImpl(
r'capabilities',
35651587,
-1,
-1,
6,
7,
const <int>[5],
const <int>[],
const prefix0.ContainedReflectable(),
const []),
r.MethodMirrorImpl(
r'canReflect',
2097154,
-1,
-1,
1,
1,
const <int>[],
const <int>[2],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'reflect',
2097154,
-1,
-1,
8,
8,
const <int>[],
const <int>[3],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'canReflectType',
2097154,
-1,
-1,
1,
1,
const <int>[],
const <int>[4],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'reflectType',
2097154,
-1,
-1,
9,
9,
const <int>[],
const <int>[5],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'findLibrary',
2097154,
-1,
-1,
10,
10,
const <int>[],
const <int>[6],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'libraries',
35651587,
-1,
-1,
12,
13,
const <int>[11, 10],
const <int>[],
const prefix0.ContainedReflectable(),
const <Object>[override]),
r.MethodMirrorImpl(
r'annotatedClasses',
35651587,
-1,
-1,
15,
16,
const <int>[14],
const <int>[],
const prefix0.ContainedReflectable(),
const <Object>[override])
],
<m.ParameterMirror>[
r.ParameterMirrorImpl(
r'other',
134348806,
1,
const prefix0.ContainedReflectable(),
-1,
17,
17,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'invocation',
134348806,
3,
const prefix0.ContainedReflectable(),
-1,
18,
18,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'reflectee',
134348806,
7,
const prefix0.ContainedReflectable(),
-1,
17,
17,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'reflectee',
134348806,
8,
const prefix0.ContainedReflectable(),
-1,
17,
17,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'type',
134348806,
9,
const prefix0.ContainedReflectable(),
-1,
4,
4,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'type',
134348806,
10,
const prefix0.ContainedReflectable(),
-1,
4,
4,
const <int>[],
const [],
null,
null),
r.ParameterMirrorImpl(
r'libraryName',
134348806,
11,
const prefix0.ContainedReflectable(),
-1,
2,
2,
const <int>[],
const [],
null,
null)
],
<Type>[
prefix0.ContainedReflectable,
bool,
String,
int,
Type,
prefix1.ReflectCapability,
const m.TypeValue<List<prefix1.ReflectCapability>>().type,
List,
prefix2.InstanceMirror,
prefix2.TypeMirror,
prefix2.LibraryMirror,
Uri,
const m.TypeValue<Map<Uri, prefix2.LibraryMirror>>().type,
Map,
prefix2.ClassMirror,
const m.TypeValue<Iterable<prefix2.ClassMirror>>().type,
Iterable,
Object,
Invocation
],
1,
{
r'==': (dynamic instance) => (x) => instance == x,
r'toString': (dynamic instance) => instance.toString,
r'noSuchMethod': (dynamic instance) => instance.noSuchMethod,
r'hashCode': (dynamic instance) => instance.hashCode,
r'runtimeType': (dynamic instance) => instance.runtimeType,
r'capabilities': (dynamic instance) => instance.capabilities,
r'canReflect': (dynamic instance) => instance.canReflect,
r'reflect': (dynamic instance) => instance.reflect,
r'canReflectType': (dynamic instance) => instance.canReflectType,
r'reflectType': (dynamic instance) => instance.reflectType,
r'findLibrary': (dynamic instance) => instance.findLibrary,
r'libraries': (dynamic instance) => instance.libraries,
r'annotatedClasses': (dynamic instance) => instance.annotatedClasses
},
{},
<m.LibraryMirror>[
r.LibraryMirrorImpl(
r'',
Uri.parse(r'reflectable://0/'),
const prefix0.ContainedReflectable(),
const <int>[],
{},
{},
const [],
null)
],
[])
};
final _memberSymbolMap = null;
void initializeReflectable() {
r.data = _data;
r.memberSymbolMap = _memberSymbolMap;
}

View file

@ -0,0 +1,46 @@
import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
@Expose('/controller', method: 'GET')
class MyController extends Controller {
@Expose('/', method: 'GET')
Future<String> route1(RequestContext req, ResponseContext res) async {
return "My route";
}
}
@Expose('/sales', middleware: [process1])
class SalesController extends Controller {
@Expose('/', middleware: [process2])
Future<String> route1(RequestContext req, ResponseContext res) async {
return "Sales route";
}
}
bool process1(RequestContext req, ResponseContext res) {
res.write('Hello, ');
return true;
}
bool process2(RequestContext req, ResponseContext res) {
res.write('From Sales, ');
return true;
}
void main() async {
// Using Mirror Reflector
var app = Angel(reflector: MirrorsReflector());
// My Controller
app.container.registerSingleton<MyController>(MyController());
await app.mountController<MyController>();
// Sales Controller
app.container.registerSingleton<SalesController>(SalesController());
await app.mountController<SalesController>();
var http = AngelHttp(app);
var server = await http.startServer('localhost', 3000);
print("Angel server listening at ${http.uri}");
}

View file

@ -0,0 +1,63 @@
import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
class Todo extends Model {
String? text;
String? over;
Todo({this.text, this.over});
Map<String, dynamic> toJson() {
return {
'text': text,
'over': over,
};
}
}
@Expose('/todo', method: 'GET')
class TodoController extends Controller {
@Expose('/')
Todo todo(Todo singleton) => singleton;
}
@Expose('/controller', method: 'GET')
class MyController extends Controller {
@Expose('/', method: 'GET')
Future<String> route1(RequestContext req, ResponseContext res) async {
return "My route";
}
//Todo todo(Todo singleton) => singleton;
}
@Expose('/sales', middleware: [process1])
class SalesController extends Controller {
@Expose('/', middleware: [process2])
Future<String> route1(RequestContext req, ResponseContext res) async {
return "Sales route";
}
}
bool process1(RequestContext req, ResponseContext res) {
res.write('Hello, ');
return true;
}
bool process2(RequestContext req, ResponseContext res) {
res.write('From Sales, ');
return true;
}
void main() async {
// Using Mirror Reflector
var app = Angel(reflector: MirrorsReflector());
await app.configure(MyController().configureServer);
await app.configure(SalesController().configureServer);
var http = AngelHttp(app);
var server = await http.startServer('localhost', 3000);
print("Angel server listening at ${http.uri}");
}

View file

@ -0,0 +1,72 @@
import 'package:angel3_container_generator/angel3_container_generator.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
import 'example3_controller.reflectable.dart';
@contained
@Expose('/controller', method: 'GET')
class MyController extends Controller {
@Expose('/')
Order order(Order singleton) => singleton;
//Todo todo(Todo singleton) => singleton;
}
class Todo extends Model {
String? text;
String? over;
Todo({this.text, this.over});
Map<String, dynamic> toJson() {
return {
'text': text,
'over': over,
};
}
}
class FoodItem {
final String name;
final num price;
final num qty;
FoodItem(this.name, this.price, this.qty);
}
class Order {
FoodItem item;
String? get name => item.name;
Order(this.item);
}
void main() async {
//var reflector = const GeneratedReflector();
//Container container = Container(reflector);
//container.registerSingleton<SalesController>(SalesController());
// Using GeneratedReflector
initializeReflectable();
var app = Angel(reflector: GeneratedReflector());
// Using MirrorReflector
//var app = Angel(reflector: MirrorsReflector());
//await app.configure(MyController().configureServer);
// My Controller
//app.container.registerSingleton<MyController>(MyController());
//await app.mountController<MyController>();
await app.configure(MyController().configureServer);
// Sales Controller
//app.container.registerSingleton<SalesController>(SalesController());
//await app.mountController<SalesController>();
var http = AngelHttp(app);
var server = await http.startServer('localhost', 3000);
print("Angel server listening at ${http.uri}");
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,44 @@
import 'package:example2/src/models.dart';
void main() {
final stopwatch = Stopwatch()..start();
//var reflectedClass = reflect(Shape());
//reflectedClass.invoke(#draw, []);
//reflectedClass.invoke(Symbol('draw'), []);
print('Reflection executed in ${stopwatch.elapsed.inMilliseconds} ms');
stopwatch.stop();
//printAnnotationValue(String);
//printAnnotationValue(Shape);
//printAnnotationValue(Square);
}
class Shape {
void draw() => print("Draw Shape");
}
@Person('Will', 'Tom')
class Square {
void greetHii() {
print("Hii Welcome to flutter agency");
}
}
/*
void printAnnotationValue(final Type clazz) {
final DeclarationMirror clazzDeclaration = reflectClass(clazz);
final ClassMirror someAnnotationMirror = reflectClass(Person);
final annotationInstsanceMirror =
clazzDeclaration.metadata.where((d) => d.type == someAnnotationMirror);
if (annotationInstsanceMirror.isEmpty) {
print('No annotated class found');
return;
}
final someAnnotationInstance =
(annotationInstsanceMirror.first.reflectee as Person);
print(someAnnotationInstance.firstName);
}
*/

View file

@ -0,0 +1,9 @@
targets:
$default:
builders:
reflectable:
generate_for:
#- lib/**_controller.dart
- bin/**_controller.dart
options:
formatted: true

View file

@ -0,0 +1,15 @@
import 'package:angel3_container_generator/angel3_container_generator.dart';
import 'package:angel3_framework/angel3_framework.dart';
@Expose('/hr')
class HrController extends Controller {
@Expose('/')
landingPage() => "Hello, world!";
}
@contained
class SalesController extends Controller {
landingPage() => "Hello, world!";
}
void main() {}

View file

@ -0,0 +1,5 @@
class Person {
final String firstName;
final String lastName;
const Person(this.firstName, this.lastName);
}

View file

@ -2,10 +2,10 @@ name: example2
version: 0.0.1 version: 0.0.1
description: Example 2. description: Example 2.
environment: environment:
sdk: '>=2.18.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_container: ^7.0.0 angel3_container: ^7.1.0-beta.1
angel3_container_generator: ^7.0.0 angel3_container_generator: ^7.1.0-beta.1
angel3_http_exception: ^7.0.0 angel3_http_exception: ^7.0.0
angel3_framework: ^7.0.0 angel3_framework: ^7.0.0
angel3_model: ^7.0.0 angel3_model: ^7.0.0
@ -30,16 +30,20 @@ dependencies:
tuple: ^2.0.0 tuple: ^2.0.0
uuid: ^3.0.1 uuid: ^3.0.1
collection: ^1.15.0 collection: ^1.15.0
reflectable: ^4.0.2
dev_dependencies: dev_dependencies:
build_runner: ^2.1.2
http: ^0.13.1 http: ^0.13.1
io: ^1.0.0 io: ^1.0.0
test: ^1.21.0 test: ^1.21.0
lints: ^2.0.0 lints: ^2.0.0
# dependency_overrides: # dependency_overrides:
# angel3_container: # angel3_container:
# path: ../container/angel_container # path: ../../../packages/container/angel_container
# angel3_http_exception: # angel3_container_generator:
# path: ../http_exception # path: ../../../packages/container/angel_container_generator
# angel3_framework:
# path: ../../../packages/framework
# angel3_model: # angel3_model:
# path: ../model # path: ../model
# angel3_route: # angel3_route:

View file

@ -0,0 +1,14 @@
import 'package:angel3_container_generator/angel3_container_generator.dart';
import 'package:angel3_framework/angel3_framework.dart';
@Expose('/hr')
class HrController extends Controller {
@Expose('/')
landingPage() => "Hello, world!";
}
@contained
class SalesController extends Controller {
landingPage() => "Hello, world!";
}

View file

@ -3,7 +3,7 @@ version: 1.0.0
description: Angel3 performance testing tool description: Angel3 performance testing tool
publish_to: none publish_to: none
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
published_to: none published_to: none
dependencies: dependencies:
mysql1: ^0.20.0 mysql1: ^0.20.0

View file

@ -3,7 +3,7 @@ version: 1.0.0
description: Angel3 performance testing tool description: Angel3 performance testing tool
publish_to: none publish_to: none
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
published_to: none published_to: none
dependencies: dependencies:
http: ^0.13.4 http: ^0.13.4

View file

@ -3,7 +3,7 @@ version: 1.0.0
description: Angel3 performance testing tool description: Angel3 performance testing tool
publish_to: none publish_to: none
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
published_to: none published_to: none
dependencies: dependencies:
http: ^0.13.4 http: ^0.13.4

View file

@ -1,5 +1,15 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Upgraded `http` to 1.0.0
* Fixed failed `successRedirect` test case
* Fixed failed `failureRedirect` test case
* Fixed failed `login` test case
* Fixed failed `force basic` test case
* Added `example1` and `example2`
## 7.0.1 ## 7.0.1
* Fixed linter warnings * Fixed linter warnings

View file

@ -20,7 +20,7 @@ Ensure you have read the [User Guide](https://angel3-docs.dukefirehawk.com/guide
configureServer(Angel app) async { configureServer(Angel app) async {
var auth = AngelAuth<User>( var auth = AngelAuth<User>(
serializer: (user) => user.id ?? '', serializer: (user) => user.id ?? '',
deserializer: (id) => fetchAUserByIdSomehow(id) deserializer: (id) => fetchAUserByIdSomehow(id
); );
auth.strategies['local'] = LocalAuthStrategy(...); auth.strategies['local'] = LocalAuthStrategy(...);

View file

@ -0,0 +1,22 @@
### Load landing page
GET http://localhost:3000/ HTTP/1.1
### login (call_back)
POST http://localhost:3000/login HTTP/1.1
Content-Type: application/json
Authorization: Basic jdoe1:password
### Success redirect (local)
POST http://localhost:3000/login HTTP/1.1
Content-Type: application/json
Authorization: Basic username:password
### Failure redirect (local)
POST http://localhost:3000/login HTTP/1.1
Content-Type: application/json
Authorization: Basic password:username
### Force basic
GET http://localhost:3000/hello HTTP/1.1
Content-Type: application/json
Accept:application/json

View file

@ -0,0 +1,113 @@
import 'package:angel3_auth/angel3_auth.dart';
import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
import 'package:collection/collection.dart' show IterableExtension;
import 'package:io/ansi.dart';
import 'package:logging/logging.dart';
import 'package:collection/collection.dart';
class User extends Model {
String? username, password;
User({this.username, this.password});
static User parse(Map<String, dynamic> map) {
return User(
username: map['username'],
password: map['password'],
);
}
Map<String, dynamic> toJson() {
return {
'id': id,
'username': username,
'password': password,
'created_at': createdAt?.toIso8601String(),
'updated_at': updatedAt?.toIso8601String()
};
}
}
/*
* Backend for callback test cases
*/
void main() async {
hierarchicalLoggingEnabled = true;
Angel app = Angel(reflector: MirrorsReflector());
AngelHttp angelHttp = AngelHttp(app);
app.use('/users', MapService());
var oldErrorHandler = app.errorHandler;
app.errorHandler = (e, req, res) {
app.logger.severe(e.message, e, e.stackTrace ?? StackTrace.current);
return oldErrorHandler(e, req, res);
};
app.logger = Logger('angel3_auth')
..level = Level.FINEST
..onRecord.listen((rec) {
print(rec);
if (rec.error != null) {
print(yellow.wrap(rec.error.toString()));
}
if (rec.stackTrace != null) {
print(yellow.wrap(rec.stackTrace.toString()));
}
});
await app
.findService('users')
?.create({'username': 'jdoe1', 'password': 'password'});
var auth = AngelAuth<User>(
serializer: (u) => u.id ?? '',
deserializer: (id) async =>
await app.findService('users')?.read(id) as User);
//auth.serializer = (u) => u.id;
//auth.deserializer =
// (id) async => await app.findService('users')!.read(id) as User;
await app.configure(auth.configureServer);
auth.strategies['local'] = LocalAuthStrategy((username, password) async {
var users = await app
.findService('users')
?.index()
.then((it) => it.map<User>((m) => User.parse(m)).toList());
var result = users?.firstWhereOrNull(
(user) => user.username == username && user.password == password);
return Future.value(result);
}, allowBasic: true);
app.post(
'/login',
auth.authenticate('local', AngelAuthOptions(callback: (req, res, token) {
res
..write('Hello!')
..close();
})));
app.get('/', (req, res) => res.write("Hello"));
app.chain([
(req, res) {
if (!req.container!.has<User>()) {
req.container!.registerSingleton<User>(
User(username: req.params['name']?.toString()));
}
return true;
}
]).post(
'/existing/:name',
auth.authenticate('local'),
);
await angelHttp.startServer('127.0.0.1', 3000);
}

View file

@ -0,0 +1,67 @@
import 'dart:async';
import 'package:angel3_auth/angel3_auth.dart';
import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
import 'package:logging/logging.dart';
final Map<String, String> sampleUser = {'hello': 'world'};
final AngelAuth<Map<String, String>> auth = AngelAuth<Map<String, String>>(
serializer: (user) async => '1337', deserializer: (id) async => sampleUser);
//var headers = <String, String>{'accept': 'application/json'};
var localOpts = AngelAuthOptions<Map<String, String>>(
failureRedirect: '/failure', successRedirect: '/success');
var localOpts2 =
AngelAuthOptions<Map<String, String>>(canRespondWithJson: false);
Future<Map<String, String>> verifier(String? username, String? password) async {
if (username == 'username' && password == 'password') {
return sampleUser;
} else {
return {};
}
}
Future wireAuth(Angel app) async {
//auth.strategies['local'] = LocalAuthStrategy(verifier);
auth.strategies['local'] =
LocalAuthStrategy(verifier, forceBasic: true, realm: 'test');
await app.configure(auth.configureServer);
}
/*
* Backend for local test cases
*/
void main() async {
Angel app = Angel(reflector: MirrorsReflector());
AngelHttp angelHttp = AngelHttp(app, useZone: false);
await app.configure(wireAuth);
app.get('/hello', (req, res) {
// => 'Woo auth'
return 'Woo auth';
}, middleware: [auth.authenticate('local', localOpts2)]);
app.post('/login', (req, res) => 'This should not be shown',
middleware: [auth.authenticate('local', localOpts)]);
app.get('/success', (req, res) => 'yep', middleware: [
requireAuthentication<Map<String, String>>(),
]);
app.get('/failure', (req, res) => 'nope');
app.logger = Logger('local_test')
..onRecord.listen((rec) {
print(
'${rec.time}: ${rec.level.name}: ${rec.loggerName}: ${rec.message}');
if (rec.error != null) {
print(rec.error);
print(rec.stackTrace);
}
});
await angelHttp.startServer('127.0.0.1', 3000);
}

View file

@ -5,8 +5,6 @@ import 'package:angel3_framework/angel3_framework.dart';
import '../options.dart'; import '../options.dart';
import '../strategy.dart'; import '../strategy.dart';
bool _validateString(String? str) => str != null && str.isNotEmpty;
/// Determines the validity of an incoming username and password. /// Determines the validity of an incoming username and password.
// typedef FutureOr<User> LocalAuthVerifier<User>(String? username, String? password); // typedef FutureOr<User> LocalAuthVerifier<User>(String? username, String? password);
typedef LocalAuthVerifier<User> = FutureOr<User?> Function( typedef LocalAuthVerifier<User> = FutureOr<User?> Function(
@ -30,7 +28,7 @@ class LocalAuthStrategy<User> extends AuthStrategy<User> {
{this.usernameField = 'username', {this.usernameField = 'username',
this.passwordField = 'password', this.passwordField = 'password',
this.invalidMessage = 'Please provide a valid username and password.', this.invalidMessage = 'Please provide a valid username and password.',
this.allowBasic = true, this.allowBasic = false,
this.forceBasic = false, this.forceBasic = false,
this.realm = 'Authentication is required.'}) { this.realm = 'Authentication is required.'}) {
_log.info('Using LocalAuthStrategy'); _log.info('Using LocalAuthStrategy');
@ -68,26 +66,52 @@ class LocalAuthStrategy<User> extends AuthStrategy<User> {
return null; return null;
} }
return verificationResult; //Allow non-null to pass through
//return verificationResult;
} }
} } else {
if (verificationResult == null) {
var body = await req var body = await req
.parseBody() .parseBody()
.then((_) => req.bodyAsMap) .then((_) => req.bodyAsMap)
.catchError((_) => <String, dynamic>{}); .catchError((_) => <String, dynamic>{});
//if (body != null) { if (_validateString(body[usernameField]?.toString()) &&
if (_validateString(body[usernameField].toString()) && _validateString(body[passwordField]?.toString())) {
_validateString(body[passwordField].toString())) {
verificationResult = await verifier( verificationResult = await verifier(
body[usernameField].toString(), body[passwordField].toString()); body[usernameField]?.toString(), body[passwordField]?.toString());
} }
//}
} }
if (verificationResult == null || // User authentication succeeded can return Map(one element), User(non null) or true
(verificationResult is Map && verificationResult.isEmpty)) { if (verificationResult != null && verificationResult != false) {
if (verificationResult is Map && verificationResult.isNotEmpty) {
return verificationResult;
} else if (verificationResult is! Map) {
return verificationResult;
}
}
// Force basic if set
if (forceBasic) {
//res.headers['www-authenticate'] = 'Basic realm="$realm"';
res
..statusCode = 401
..headers['www-authenticate'] = 'Basic realm="$realm"';
await res.close();
return null;
}
// Redirect failed authentication
if (localOptions.failureRedirect != null &&
localOptions.failureRedirect!.isNotEmpty) {
await res.redirect(localOptions.failureRedirect, code: 401);
return null;
}
_log.info('Not authenticated');
throw AngelHttpException.notAuthenticated();
/*
if (verificationResult is Map && verificationResult.isEmpty) {
if (localOptions.failureRedirect != null && if (localOptions.failureRedirect != null &&
localOptions.failureRedirect!.isNotEmpty) { localOptions.failureRedirect!.isNotEmpty) {
await res.redirect(localOptions.failureRedirect, code: 401); await res.redirect(localOptions.failureRedirect, code: 401);
@ -107,5 +131,8 @@ class LocalAuthStrategy<User> extends AuthStrategy<User> {
_log.info('Not authenticated'); _log.info('Not authenticated');
throw AngelHttpException.notAuthenticated(); throw AngelHttpException.notAuthenticated();
} }
*/
} }
bool _validateString(String? str) => str != null && str.isNotEmpty;
} }

View file

@ -1,35 +1,35 @@
name: angel3_auth name: angel3_auth
description: A complete authentication plugin for Angel3. Includes support for stateless JWT tokens, Basic Auth, and more. description: A complete authentication plugin for Angel3. Includes support for stateless JWT tokens, Basic Auth, and more.
version: 7.0.1 version: 8.0.0
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
charcode: ^1.2.0 charcode: ^1.3.0
collection: ^1.15.0 collection: ^1.17.0
crypto: ^3.0.0 crypto: ^3.0.0
http_parser: ^4.0.0 http_parser: ^4.0.0
meta: ^1.3.0 meta: ^1.9.0
quiver: ^3.0.0 quiver: ^3.2.0
logging: ^1.0.0 logging: ^1.2.0
dev_dependencies: dev_dependencies:
angel3_container: ^7.0.0 angel3_container: ^8.0.0
http: ^0.13.1 http: ^1.0.0
io: ^1.0.0 io: ^1.0.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request

View file

@ -16,7 +16,7 @@ class User extends Model {
User({this.username, this.password}); User({this.username, this.password});
static User parse(Map map) { static User parse(Map<String, dynamic> map) {
return User( return User(
username: map['username'] as String?, username: map['username'] as String?,
password: map['password'] as String?, password: map['password'] as String?,
@ -41,6 +41,7 @@ void main() {
http.Client? client; http.Client? client;
HttpServer server; HttpServer server;
String? url; String? url;
String? encodedAuth;
setUp(() async { setUp(() async {
hierarchicalLoggingEnabled = true; hierarchicalLoggingEnabled = true;
@ -54,7 +55,7 @@ void main() {
return oldErrorHandler(e, req, res); return oldErrorHandler(e, req, res);
}; };
app.logger = Logger('angel_auth') app.logger = Logger('angel3_auth')
..level = Level.FINEST ..level = Level.FINEST
..onRecord.listen((rec) { ..onRecord.listen((rec) {
print(rec); print(rec);
@ -86,13 +87,13 @@ void main() {
var users = await app var users = await app
.findService('users') .findService('users')
?.index() ?.index()
.then((it) => it.map<User>((m) => User.parse(m as Map)).toList()); .then((it) => it.map<User>((m) => User.parse(m)).toList());
var result = users?.firstWhereOrNull( var result = users?.firstWhereOrNull(
(user) => user.username == username && user.password == password); (user) => user.username == username && user.password == password);
return Future.value(result); return Future.value(result);
}); }, allowBasic: true);
app.post( app.post(
'/login', '/login',
@ -116,6 +117,8 @@ void main() {
auth.authenticate('local'), auth.authenticate('local'),
); );
encodedAuth = base64.encode(utf8.encode('jdoe1:password'));
client = http.Client(); client = http.Client();
server = await angelHttp.startServer(); server = await angelHttp.startServer();
url = 'http://${server.address.address}:${server.port}'; url = 'http://${server.address.address}:${server.port}';
@ -131,7 +134,7 @@ void main() {
test('login', () async { test('login', () async {
final response = await client!.post(Uri.parse('$url/login'), final response = await client!.post(Uri.parse('$url/login'),
body: {'username': 'jdoe1', 'password': 'password'}); headers: {'Authorization': 'Basic $encodedAuth'});
print('Response: ${response.body}'); print('Response: ${response.body}');
expect(response.body, equals('Hello!')); expect(response.body, equals('Hello!'));
}, },

View file

@ -1,5 +1,6 @@
import 'dart:async'; import 'dart:async';
import 'package:angel3_auth/angel3_auth.dart'; import 'package:angel3_auth/angel3_auth.dart';
import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart'; import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart'; import 'package:angel3_framework/http.dart';
import 'dart:convert'; import 'dart:convert';
@ -9,7 +10,7 @@ import 'package:test/test.dart';
final AngelAuth<Map<String, String>> auth = AngelAuth<Map<String, String>>( final AngelAuth<Map<String, String>> auth = AngelAuth<Map<String, String>>(
serializer: (user) async => '1337', deserializer: (id) async => sampleUser); serializer: (user) async => '1337', deserializer: (id) async => sampleUser);
var headers = <String, String>{'accept': 'application/json'}; //var headers = <String, String>{'accept': 'application/json'};
var localOpts = AngelAuthOptions<Map<String, String>>( var localOpts = AngelAuthOptions<Map<String, String>>(
failureRedirect: '/failure', successRedirect: '/success'); failureRedirect: '/failure', successRedirect: '/success');
var localOpts2 = var localOpts2 =
@ -29,7 +30,7 @@ Future wireAuth(Angel app) async {
//auth.serializer = (user) async => 1337; //auth.serializer = (user) async => 1337;
//auth.deserializer = (id) async => sampleUser; //auth.deserializer = (id) async => sampleUser;
auth.strategies['local'] = LocalAuthStrategy(verifier); auth.strategies['local'] = LocalAuthStrategy(verifier, allowBasic: true);
await app.configure(auth.configureServer); await app.configure(auth.configureServer);
} }
@ -42,9 +43,10 @@ void main() async {
setUp(() async { setUp(() async {
client = http.Client(); client = http.Client();
app = Angel(); app = Angel(reflector: MirrorsReflector());
angelHttp = AngelHttp(app, useZone: false); angelHttp = AngelHttp(app, useZone: false);
await app.configure(wireAuth); await app.configure(wireAuth);
app.get('/hello', (req, res) { app.get('/hello', (req, res) {
// => 'Woo auth' // => 'Woo auth'
return 'Woo auth'; return 'Woo auth';
@ -88,19 +90,21 @@ void main() async {
}); });
test('successRedirect', () async { test('successRedirect', () async {
var postData = {'username': 'username', 'password': 'password'}; //var postData = {'username': 'username', 'password': 'password'};
var encodedAuth = base64.encode(utf8.encode('username:password'));
var response = await client.post(Uri.parse('$url/login'), var response = await client.post(Uri.parse('$url/login'),
body: json.encode(postData), headers: {'Authorization': 'Basic $encodedAuth'});
headers: {'content-type': 'application/json'});
expect(response.statusCode, equals(302)); expect(response.statusCode, equals(302));
expect(response.headers['location'], equals('/success')); expect(response.headers['location'], equals('/success'));
}); });
test('failureRedirect', () async { test('failureRedirect', () async {
var postData = {'username': 'password', 'password': 'username'}; //var postData = {'username': 'password', 'password': 'username'};
var encodedAuth = base64.encode(utf8.encode('password:username'));
var response = await client.post(Uri.parse('$url/login'), var response = await client.post(Uri.parse('$url/login'),
body: json.encode(postData), headers: {'Authorization': 'Basic $encodedAuth'});
headers: {'content-type': 'application/json'});
print('Status Code: ${response.statusCode}'); print('Status Code: ${response.statusCode}');
print(response.headers); print(response.headers);
print(response.body); print(response.body);

View file

@ -11,7 +11,7 @@ void main() {
secureCookies: true, secureCookies: true,
cookieDomain: 'SECURE', cookieDomain: 'SECURE',
jwtLifeSpan: threeDays.inMilliseconds, jwtLifeSpan: threeDays.inMilliseconds,
serializer: (u) => u as String, serializer: (u) => u,
deserializer: (u) => u); deserializer: (u) => u);
setUp(() => defaultCookie = Cookie('a', 'b')); setUp(() => defaultCookie = Cookie('a', 'b'));

View file

@ -1,5 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Issue: `oauth2` does not support `http` 1.0.0
## 7.0.1 ## 7.0.1
* Updated example * Updated example

View file

@ -1,30 +1,30 @@
name: angel3_auth_oauth2 name: angel3_auth_oauth2
version: 7.0.1 version: 8.0.0
description: Angel3 library for authenticating users with external identity providers via OAuth2. description: Angel3 library for authenticating users with external identity providers via OAuth2.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth_oauth2 repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth_oauth2
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_auth: ^7.0.0 angel3_auth: ^8.0.0
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
http_parser: ^4.0.0 http_parser: ^4.0.0
oauth2: ^2.0.0 oauth2: ^2.0.0
dev_dependencies: dev_dependencies:
logging: ^1.0.1 logging: ^1.2.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth

View file

@ -1,33 +1,34 @@
name: "angel3_auth_twitter" name: "angel3_auth_twitter"
description: Angel3 authentication strategy for Twitter login. Auto-signs requests. description: Angel3 authentication strategy for Twitter login. Auto-signs requests.
version: 7.0.0 version: 8.0.0
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth_twitter repository: https://github.com/dukefirehawk/angel/tree/master/packages/auth_twitter
publish_to: none publish_to: none
environment: environment:
sdk: ">=2.17.0 <3.0.0" sdk: ">=3.0.0 <4.0.0"
published_to: none
dependencies: dependencies:
angel3_auth: ^7.0.0 angel3_auth: ^8.0.0
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
http: ^0.13.0 http: ^1.0.0
path: ^1.0.0 path: ^1.0.0
oauth1: ^2.0.0 oauth1: ^2.0.0
dart_twitter_api: ^0.5.6+1 dart_twitter_api: ^0.5.6+1
dev_dependencies: dev_dependencies:
logging: ^1.0.0 logging: ^1.2.0
lints: ^1.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,42 +1,42 @@
name: angel3_cache name: angel3_cache
version: 7.0.0 version: 8.0.0
description: A service that provides HTTP caching to the response data for Angel3 description: A service that provides HTTP caching to the response data for Angel3
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/cache repository: https://github.com/dukefirehawk/angel/tree/master/packages/cache
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
collection: ^1.15.0 collection: ^1.17.0
meta: ^1.4.0 meta: ^1.9.0
pool: ^1.5.0 pool: ^1.5.0
logging: ^1.0.0 logging: ^1.2.0
dev_dependencies: dev_dependencies:
angel3_test: ^7.0.0 angel3_test: ^8.0.0
glob: ^2.0.1 glob: ^2.0.1
http: ^0.13.3 http: ^1.0.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_test: angel3_test:
# path: ../test path: ../test
# angel3_websocket: angel3_websocket:
# path: ../websocket path: ../websocket
# angel3_client: angel3_client:
# path: ../client path: ../client
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth
# angel3_validate: angel3_validate:
# path: ../validate path: ../validate

View file

@ -1,5 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Updated `http` to 1.0.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -0,0 +1,11 @@
import 'package:angel3_client/io.dart' as c;
void main() async {
c.Angel client = c.Rest('http://localhost:3000');
const Map<String, String> user = {'username': 'foo', 'password': 'bar'};
var localAuth = await client.authenticate(type: 'local', credentials: user);
print('JWT: ${localAuth.token}');
print('Data: ${localAuth.data}');
}

View file

@ -0,0 +1,35 @@
import 'package:angel3_auth/angel3_auth.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
import 'package:logging/logging.dart';
void main() async {
const Map<String, String> user = {'username': 'foo', 'password': 'bar'};
var localOpts =
AngelAuthOptions<Map<String, String>>(canRespondWithJson: true);
Angel app = Angel();
AngelHttp http = AngelHttp(app, useZone: false);
var auth = AngelAuth(
serializer: (_) async => 'baz', deserializer: (_) async => user);
auth.strategies['local'] = LocalAuthStrategy((username, password) async {
if (username == 'foo' && password == 'bar') {
return user;
}
return {};
}, allowBasic: false);
app.post('/auth/local', auth.authenticate('local', localOpts));
await app.configure(auth.configureServer);
app.logger = Logger('auth_test')
..onRecord.listen((rec) {
print(
'${rec.time}: ${rec.level.name}: ${rec.loggerName}: ${rec.message}');
});
await http.startServer('127.0.0.1', 3000);
}

View file

@ -1,41 +1,41 @@
name: angel3_client name: angel3_client
version: 7.0.0 version: 8.0.0
description: A browser, mobile and command line based client that supports querying Angel3 servers description: A browser, mobile and command line based client that supports querying Angel3 servers
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/client repository: https://github.com/dukefirehawk/angel/tree/master/packages/client
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_http_exception: ^7.0.0 angel3_http_exception: ^8.0.0
belatuk_json_serializer: ^6.0.0 belatuk_json_serializer: ^7.0.0
collection: ^1.15.0 collection: ^1.17.0
http: ^0.13.1 http: ^1.0.0
meta: ^1.3.0 meta: ^1.9.0
path: ^1.8.0 path: ^1.8.0
logging: ^1.0.0 logging: ^1.1.0
dev_dependencies: dev_dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
angel3_model: ^7.0.0 angel3_model: ^8.0.0
angel3_mock_request: ^7.0.0 angel3_mock_request: ^8.0.0
angel3_container: ^7.0.0 angel3_container: ^8.0.0
angel3_auth: ^7.0.0 angel3_auth: ^8.0.0
async: ^2.6.1 async: ^2.11.0
build_runner: ^2.1.2 build_runner: ^2.4.0
build_web_compilers: ^3.2.1 build_web_compilers: ^4.0.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,32 +1,32 @@
name: angel3_configuration name: angel3_configuration
version: 7.0.0 version: 8.0.0
description: Automatic YAML application configuration loader for Angel 3, with .env support. description: Automatic YAML application configuration loader for Angel 3, with .env support.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/configuration repository: https://github.com/dukefirehawk/angel/tree/master/packages/configuration
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
belatuk_merge_map: ^4.0.0 belatuk_merge_map: ^5.0.0
dotenv: ^4.0.0 dotenv: ^4.1.0
file: ^6.1.0 file: ^7.0.0
yaml: ^3.1.0 yaml: ^3.1.0
dev_dependencies: dev_dependencies:
io: ^1.0.0 io: ^1.0.0
logging: ^1.0.1 logging: ^1.2.0
lints: ^2.0.0 lints: ^2.1.0
belatuk_pretty_logging: ^5.0.0 belatuk_pretty_logging: ^6.0.0
test: ^1.21.0 test: ^1.24.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request

View file

@ -1,8 +1,19 @@
# Change Log # Change Log
## 7.1.0 ## 8.0.0
* Require Dart >= 3.0
## 7.1.0-beta.2
* Require Dart >= 2.19
* Refactored `EmptyReflector`
## 7.1.0-beta.1
* Require Dart >= 2.18 * Require Dart >= 2.18
* Moved `defaultErrorMessage` to `ContainerConst` class to resolve reflectatable issue.
* Added `hashCode`
## 7.0.0 ## 7.0.0

View file

@ -5,8 +5,41 @@
[![Gitter](https://img.shields.io/gitter/room/angel_dart/discussion)](https://gitter.im/angel_dart/discussion) [![Gitter](https://img.shields.io/gitter/room/angel_dart/discussion)](https://gitter.im/angel_dart/discussion)
[![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container/LICENSE) [![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container/LICENSE)
An better IoC container for Angel3, ultimately allowing Angel3 to be used without `dart:mirrors` package. A better IoC container for Angel3, ultimately allowing Angel3 to be used with or without `dart:mirrors` package.
```dart ```dart
import 'package:angel3_container/angel3_container.dart'; import 'package:angel3_container/mirrors.dart';
import 'package:angel3_framework/angel3_framework.dart';
import 'package:angel3_framework/http.dart';
@Expose('/sales', middleware: [process1])
class SalesController extends Controller {
@Expose('/', middleware: [process2])
Future<String> route1(RequestContext req, ResponseContext res) async {
return "Sales route";
}
}
bool process1(RequestContext req, ResponseContext res) {
res.write('Hello, ');
return true;
}
bool process2(RequestContext req, ResponseContext res) {
res.write('From Sales, ');
return true;
}
void main() async {
// Using Mirror Reflector
var app = Angel(reflector: MirrorsReflector());
// Sales Controller
app.container.registerSingleton<SalesController>(SalesController());
await app.mountController<SalesController>();
var http = AngelHttp(app);
var server = await http.startServer('localhost', 3000);
print("Angel3 server listening at ${http.uri}");
}
``` ```

View file

@ -6,3 +6,4 @@ export 'src/static/static.dart';
export 'src/exception.dart'; export 'src/exception.dart';
export 'src/reflector.dart'; export 'src/reflector.dart';
export 'src/throwing.dart'; export 'src/throwing.dart';
export 'src/container_const.dart';

View file

@ -0,0 +1,8 @@
class ContainerConst {
static const String defaultErrorMessage =
'You attempted to perform a reflective action, but you are using `ThrowingReflector`, '
'a class which disables reflection. Consider using the `MirrorsReflector` '
'class if you need reflection.';
ContainerConst._();
}

View file

@ -61,11 +61,6 @@ class _EmptyReflectedClass extends ReflectedClass {
bool isAssignableTo(ReflectedType? other) { bool isAssignableTo(ReflectedType? other) {
return other == this; return other == this;
} }
@override
bool operator ==(other) {
return other is ReflectedClass && other.hashCode == hashCode;
}
} }
class _EmptyReflectedType extends ReflectedType { class _EmptyReflectedType extends ReflectedType {
@ -85,22 +80,12 @@ class _EmptyReflectedType extends ReflectedType {
bool isAssignableTo(ReflectedType? other) { bool isAssignableTo(ReflectedType? other) {
return other == this; return other == this;
} }
@override
bool operator ==(other) {
return other is ReflectedType && other.hashCode == hashCode;
}
} }
class _EmptyReflectedInstance extends ReflectedInstance { class _EmptyReflectedInstance extends ReflectedInstance {
const _EmptyReflectedInstance() const _EmptyReflectedInstance()
: super(const _EmptyReflectedType(), const _EmptyReflectedClass(), null); : super(const _EmptyReflectedType(), const _EmptyReflectedClass(), null);
@override
bool operator ==(other) {
return other is ReflectedInstance && other.hashCode == hashCode;
}
@override @override
ReflectedInstance getField(String name) { ReflectedInstance getField(String name) {
throw UnsupportedError( throw UnsupportedError(

View file

@ -4,6 +4,8 @@ import 'dart:mirrors' as dart;
import '../exception.dart'; import '../exception.dart';
import '../reflector.dart'; import '../reflector.dart';
import 'package:quiver/core.dart';
/// A [Reflector] implementation that forwards to `dart:mirrors`. /// A [Reflector] implementation that forwards to `dart:mirrors`.
/// ///
/// Useful on the server, where reflection is supported. /// Useful on the server, where reflection is supported.
@ -176,6 +178,9 @@ class _ReflectedClassMirror extends ReflectedClass {
bool operator ==(other) { bool operator ==(other) {
return other is _ReflectedClassMirror && other.mirror == mirror; return other is _ReflectedClassMirror && other.mirror == mirror;
} }
@override
int get hashCode => hash2(mirror, " ");
} }
class _ReflectedDeclarationMirror extends ReflectedDeclaration { class _ReflectedDeclarationMirror extends ReflectedDeclaration {

View file

@ -1,3 +1,5 @@
import 'package:angel3_container/src/container_const.dart';
import 'empty/empty.dart'; import 'empty/empty.dart';
import 'reflector.dart'; import 'reflector.dart';
@ -9,12 +11,15 @@ class ThrowingReflector extends Reflector {
/// The error message to give the end user when an [UnsupportedError] is thrown. /// The error message to give the end user when an [UnsupportedError] is thrown.
final String errorMessage; final String errorMessage;
/*
static const String defaultErrorMessage = static const String defaultErrorMessage =
'You attempted to perform a reflective action, but you are using `ThrowingReflector`, ' 'You attempted to perform a reflective action, but you are using `ThrowingReflector`, '
'a class which disables reflection. Consider using the `MirrorsReflector` ' 'a class which disables reflection. Consider using the `MirrorsReflector` '
'class if you need reflection.'; 'class if you need reflection.';
*/
const ThrowingReflector({this.errorMessage = defaultErrorMessage}); const ThrowingReflector(
{this.errorMessage = ContainerConst.defaultErrorMessage});
@override @override
String? getName(Symbol symbol) => const EmptyReflector().getName(symbol); String? getName(Symbol symbol) => const EmptyReflector().getName(symbol);

View file

@ -1,13 +1,13 @@
name: angel3_container name: angel3_container
version: 7.1.0 version: 8.0.0
description: Angel3 hierarchical DI container, and pluggable backends for reflection. description: Angel3 hierarchical DI container, and pluggable backends for reflection.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container repository: https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container
environment: environment:
sdk: '>=2.18.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
collection: ^1.15.0 collection: ^1.17.0
quiver: ^3.0.1 quiver: ^3.2.0
dev_dependencies: dev_dependencies:
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0

View file

@ -1,8 +1,12 @@
# Change Log # Change Log
## 7.1.0 ## 8.0.0
* Require Dart >= 2.18 * Require Dart >= 3.0
## 7.1.0-beta.1
* Require Dart >= 2.19
* Upgraded `relectable` to 4.x.x * Upgraded `relectable` to 4.x.x
## 7.0.0 ## 7.0.0

View file

@ -5,4 +5,27 @@
[![Gitter](https://img.shields.io/gitter/room/angel_dart/discussion)](https://gitter.im/angel_dart/discussion) [![Gitter](https://img.shields.io/gitter/room/angel_dart/discussion)](https://gitter.im/angel_dart/discussion)
[![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/tree/master/packages/container/angel3_container_generator/LICENSE) [![License](https://img.shields.io/github/license/dukefirehawk/angel)](https://github.com/dukefirehawk/angel/tree/master/packages/container/angel3_container_generator/LICENSE)
A better IoC container generator for Angel3, ultimately allowing Angel3 to be used without `dart:mirrors`. An alternative container for Angel3 that uses `reflectable` package instead of `dart:mirrors` for reflection. However, `reflectable` has much limited relfection capabilities when compared to `dart:mirrors`.
## Usage
* Annotable the class with `@contained`.
* Run `dart run build_runner build <Your class directory>`
* Alternatively create a `build.xml` file with the following content
```yaml
targets:
$default:
builders:
reflectable:
generate_for:
- bin/**_controller.dart
options:
formatted: true
```
## Known limitation
* Reflection on functions/closures is not supported
* Reflection on private declarations is not supported
* Reflection on generic type is not supported

View file

@ -5,8 +5,7 @@ import 'package:angel3_container_generator/angel3_container_generator.dart';
Future<void> main() async { Future<void> main() async {
// Create a container instance. // Create a container instance.
var reflector = const GeneratedReflector(); Container container = Container(GeneratedReflector());
Container container = Container(reflector);
// Register a singleton. // Register a singleton.
container.registerSingleton<Engine>(Engine(40)); container.registerSingleton<Engine>(Engine(40));

View file

@ -11,11 +11,11 @@ class ContainedReflectable extends Reflectable {
topLevelInvokeCapability, topLevelInvokeCapability,
typeAnnotationQuantifyCapability, typeAnnotationQuantifyCapability,
superclassQuantifyCapability, superclassQuantifyCapability,
instanceInvokeCapability,
libraryCapability, libraryCapability,
invokingCapability, invokingCapability,
newInstanceCapability, metadataCapability,
reflectedTypeCapability, reflectedTypeCapability,
typeCapability,
typingCapability); typingCapability);
} }

View file

@ -1,18 +1,18 @@
name: angel3_container_generator name: angel3_container_generator
version: 7.1.0 version: 8.0.0
description: Codegen support for using pkg:reflectable with pkg:angel3_container. description: Codegen support for using pkg:reflectable with pkg:angel3_container.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container_generator repository: https://github.com/dukefirehawk/angel/tree/master/packages/container/angel_container_generator
environment: environment:
sdk: '>=2.18.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_container: ^7.0.0 angel3_container: ^8.0.0
reflectable: ^4.0.2 reflectable: ^4.0.0
dev_dependencies: dev_dependencies:
build_runner: ^2.1.2 build_runner: ^2.4.0
build_test: ^2.1.3 build_test: ^2.1.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
dependency_overrides: dependency_overrides:
angel3_container: angel3_container:
path: ../angel_container path: ../angel_container

View file

@ -29,7 +29,8 @@ void main() {
expect(album.title, 'flowers by stevie wonder'); expect(album.title, 'flowers by stevie wonder');
}); });
testReflector(reflector); // Skip as pkg:reflectable cannot reflect on closures at all (yet)
//testReflector(reflector);
} }
@contained @contained
@ -49,7 +50,6 @@ void testReflector(Reflector reflector) {
expect(blazikenMirror.getField('type').reflectee, blaziken.type); expect(blazikenMirror.getField('type').reflectee, blaziken.type);
}); });
/*
group('reflectFunction', () { group('reflectFunction', () {
var mirror = reflector.reflectFunction(returnVoidFromAFunction); var mirror = reflector.reflectFunction(returnVoidFromAFunction);
@ -73,8 +73,7 @@ void testReflector(Reflector reflector) {
expect(p?.annotations, isEmpty); expect(p?.annotations, isEmpty);
expect(p?.type, reflector.reflectType(int)); expect(p?.type, reflector.reflectType(int));
}); });
}, skip: 'pkg:reflectable cannot reflect on closures at all (yet)'); }, skip: 'pkg:reflectable cannot reflect on closures at all (yet)');
*/
test('make on singleton type returns singleton', () { test('make on singleton type returns singleton', () {
expect(container.make(Pokemon), blaziken); expect(container.make(Pokemon), blaziken);
@ -111,9 +110,9 @@ void testReflector(Reflector reflector) {
expect(kantoPokemonType.isAssignableTo(pokemonType), true); expect(kantoPokemonType.isAssignableTo(pokemonType), true);
expect( expect(
() => kantoPokemonType kantoPokemonType
.isAssignableTo(container.reflector.reflectType(String)), .isAssignableTo(container.reflector.reflectType(String)),
throwsUnsupportedError); false);
}); });
} }

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,37 +1,37 @@
name: angel3_cors name: angel3_cors
version: 7.0.0 version: 8.0.0
description: Angel3 CORS middleware. Ported from expressjs/cors to Angel3 framework. description: Angel3 CORS middleware. Ported from expressjs/cors to Angel3 framework.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/cors repository: https://github.com/dukefirehawk/angel/tree/master/packages/cors
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
dev_dependencies: dev_dependencies:
angel3_test: ^7.0.0 angel3_test: ^8.0.0
http: ^0.13.3 http: ^1.0.0
lints: ^2.0.0 lints: ^2.1.0
test: ^1.21.0 test: ^1.24.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth
# angel3_client: angel3_client:
# path: ../client path: ../client
# angel3_websocket: angel3_websocket:
# path: ../websocket path: ../websocket
# angel3_validate: angel3_validate:
# path: ../validate path: ../validate
# angel3_test: angel3_test:
# path: ../test path: ../test

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,27 +1,27 @@
name: angel3_file_service name: angel3_file_service
version: 7.0.0 version: 8.0.0
description: Angel service that persists data to a file on disk, stored as a JSON list. description: Angel service that persists data to a file on disk, stored as a JSON list.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/file_service repository: https://github.com/dukefirehawk/angel/tree/master/packages/file_service
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
file: ^6.1.1 file: ^7.0.0
pool: ^1.5.0 pool: ^1.5.0
dev_dependencies: dev_dependencies:
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request

View file

@ -1,5 +1,14 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.4
* Updated `Expose` fields to non-nullable
* Updated `Controller` to use non-nullable field
## 7.0.3 ## 7.0.3
* Fixed issue #83. Allow Http request to return null headers instead of throwing an exception. * Fixed issue #83. Allow Http request to return null headers instead of throwing an exception.

View file

@ -64,13 +64,13 @@ class Controller {
} }
var routable = Routable(); var routable = Routable();
var m = router.mount(exposeDecl.path!, routable); _mountPoint = router.mount(exposeDecl.path, routable);
_mountPoint = m; //_mountPoint = m;
var typeMirror = reflector.reflectType(runtimeType); var typeMirror = reflector.reflectType(runtimeType);
// Pre-reflect methods // Pre-reflect methods
var instanceMirror = reflector.reflectInstance(this); var instanceMirror = reflector.reflectInstance(this);
final handlers = <RequestHandler>[...exposeDecl.middleware!, ...middleware]; final handlers = <RequestHandler>[...exposeDecl.middleware, ...middleware];
final routeBuilder = final routeBuilder =
_routeBuilder(reflector, instanceMirror, routable, handlers); _routeBuilder(reflector, instanceMirror, routable, handlers);
await configureRoutes(routable); await configureRoutes(routable);
@ -107,7 +107,7 @@ class Controller {
return; return;
} else { } else {
// Otherwise, create an @Expose. // Otherwise, create an @Expose.
exposeDecl = Expose(null); exposeDecl = Expose('');
} }
} }
@ -115,7 +115,7 @@ class Controller {
instanceMirror!.getField(methodName).reflectee as Function?; instanceMirror!.getField(methodName).reflectee as Function?;
var middleware = <RequestHandler>[ var middleware = <RequestHandler>[
...handlers, ...handlers,
...exposeDecl.middleware! ...exposeDecl.middleware
]; ];
var name = var name =
exposeDecl.as?.isNotEmpty == true ? exposeDecl.as : methodName; exposeDecl.as?.isNotEmpty == true ? exposeDecl.as : methodName;
@ -127,7 +127,7 @@ class Controller {
method.parameters[1].type.reflectedType == ResponseContext) { method.parameters[1].type.reflectedType == ResponseContext) {
// Create a regular route // Create a regular route
routeMappings[name ?? ''] = routable routeMappings[name ?? ''] = routable
.addRoute(exposeDecl.method, exposeDecl.path ?? '', .addRoute(exposeDecl.method, exposeDecl.path,
(RequestContext req, ResponseContext res) { (RequestContext req, ResponseContext res) {
var result = reflectedMethod!(req, res); var result = reflectedMethod!(req, res);
return result is RequestHandler ? result(req, res) : result; return result is RequestHandler ? result(req, res) : result;
@ -144,7 +144,7 @@ class Controller {
// If there is no path, reverse-engineer one. // If there is no path, reverse-engineer one.
var path = exposeDecl.path; var path = exposeDecl.path;
var httpMethod = exposeDecl.method; var httpMethod = exposeDecl.method;
if (path == null) { if (path == '') {
// Try to build a route path by finding all potential // Try to build a route path by finding all potential
// path segments, and then joining them. // path segments, and then joining them.
var parts = <String>[]; var parts = <String>[];

View file

@ -79,11 +79,6 @@ class MapService extends Service<String?, Map<String, dynamic>> {
@override @override
Future<Map<String, dynamic>> create(Map<String, dynamic> data, Future<Map<String, dynamic>> create(Map<String, dynamic> data,
[Map<String, dynamic>? params]) { [Map<String, dynamic>? params]) {
//if (data is! Map) {
// throw AngelHttpException.badRequest(
// message:
// 'MapService does not support `create` with ${data.runtimeType}.');
//}
var now = DateTime.now().toIso8601String(); var now = DateTime.now().toIso8601String();
var result = Map<String, dynamic>.from(data); var result = Map<String, dynamic>.from(data);

View file

@ -45,17 +45,17 @@ const NoExpose noExpose = NoExpose();
/// ``` /// ```
class Expose { class Expose {
final String method; final String method;
final String? path; final String path;
final Iterable<RequestHandler>? middleware; final Iterable<RequestHandler> middleware;
final String? as; final String? as;
final List<String> allowNull; final List<String> allowNull;
static const Expose get = Expose(null, method: 'GET'), static const Expose get = Expose('', method: 'GET'),
post = Expose(null, method: 'POST'), post = Expose('', method: 'POST'),
patch = Expose(null, method: 'PATCH'), patch = Expose('', method: 'PATCH'),
put = Expose(null, method: 'PUT'), put = Expose('', method: 'PUT'),
delete = Expose(null, method: 'DELETE'), delete = Expose('', method: 'DELETE'),
head = Expose(null, method: 'HEAD'); head = Expose('', method: 'HEAD');
const Expose(this.path, const Expose(this.path,
{this.method = 'GET', {this.method = 'GET',
@ -64,8 +64,8 @@ class Expose {
this.allowNull = const []}); this.allowNull = const []});
const Expose.method(this.method, const Expose.method(this.method,
{this.middleware, this.as, this.allowNull = const []}) {this.middleware = const [], this.as, this.allowNull = const []})
: path = null; : path = '';
} }
/// Used to apply special dependency injections or functionality to a function parameter. /// Used to apply special dependency injections or functionality to a function parameter.
@ -89,7 +89,7 @@ class Parameter {
final dynamic defaultValue; final dynamic defaultValue;
/// If `true` (default), then an error will be thrown if this parameter is not present. /// If `true` (default), then an error will be thrown if this parameter is not present.
final bool? required; final bool required;
const Parameter( const Parameter(
{this.cookie, {this.cookie,
@ -98,7 +98,7 @@ class Parameter {
this.session, this.session,
this.match, this.match,
this.defaultValue, this.defaultValue,
this.required}); this.required = true});
/// Returns an error that can be thrown when the parameter is not present. /// Returns an error that can be thrown when the parameter is not present.
Object? get error { Object? get error {

View file

@ -392,7 +392,7 @@ abstract class ResponseContext<RawResponse>
} }
} }
abstract class LockableBytesBuilder extends BytesBuilder { abstract class LockableBytesBuilder implements BytesBuilder {
factory LockableBytesBuilder() { factory LockableBytesBuilder() {
return _LockableBytesBuilderImpl(); return _LockableBytesBuilderImpl();
} }

View file

@ -388,7 +388,7 @@ class Angel extends Routable {
} }
static const String _reflectionErrorMessage = static const String _reflectionErrorMessage =
'${ThrowingReflector.defaultErrorMessage} $_reflectionInfo'; '${ContainerConst.defaultErrorMessage} $_reflectionInfo';
static const String _reflectionInfo = static const String _reflectionInfo =
'Features like controllers, constructor dependency injection, and `ioc` require reflection, ' 'Features like controllers, constructor dependency injection, and `ioc` require reflection, '

View file

@ -60,10 +60,10 @@ class Http2ResponseContext extends ResponseContext<ServerTransportStream> {
@override @override
BytesBuilder? get buffer => _buffer; BytesBuilder? get buffer => _buffer;
@override // @override
void addError(Object error, [StackTrace? stackTrace]) { // void addError(Object error, [StackTrace? stackTrace]) {
super.addError(error, stackTrace); // super.addError(error, stackTrace);
} // }
@override @override
void useBuffer() { void useBuffer() {

View file

@ -1,49 +1,49 @@
name: angel3_framework name: angel3_framework
version: 7.0.3 version: 8.0.0
description: A high-powered HTTP server extensible framework with dependency injection, routing and much more. description: A high-powered HTTP server extensible framework with dependency injection, routing and much more.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/framework repository: https://github.com/dukefirehawk/angel/tree/master/packages/framework
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_container: ^7.0.0 angel3_container: ^8.0.0
angel3_http_exception: ^7.0.0 angel3_http_exception: ^8.0.0
angel3_model: ^7.0.0 angel3_model: ^8.0.0
angel3_route: ^7.0.0 angel3_route: ^8.0.0
angel3_mock_request: ^7.0.0 angel3_mock_request: ^8.0.0
belatuk_merge_map: ^4.0.0 belatuk_merge_map: ^5.0.0
belatuk_combinator: ^4.0.0 belatuk_combinator: ^5.0.0
belatuk_http_server: ^3.0.0 belatuk_http_server: ^4.0.0
charcode: ^1.2.0 charcode: ^1.3.0
file: ^6.1.0 file: ^7.0.0
http_parser: ^4.0.0 http_parser: ^4.0.0
http2: ^2.0.0 http2: ^2.0.0
logging: ^1.0.0 logging: ^1.1.0
matcher: ^0.12.10 matcher: ^0.12.16
meta: ^1.3.0 meta: ^1.9.0
mime: ^1.0.0 mime: ^1.0.0
path: ^1.8.0 path: ^1.8.0
quiver: ^3.0.1 quiver: ^3.2.0
recase: ^4.0.0 recase: ^4.1.0
stack_trace: ^1.10.0 stack_trace: ^1.11.0
string_scanner: ^1.1.0 string_scanner: ^1.2.0
tuple: ^2.0.0 tuple: ^2.0.0
uuid: ^3.0.1 uuid: ^3.0.0
collection: ^1.15.0 collection: ^1.17.0
dev_dependencies: dev_dependencies:
http: ^0.13.1 http: ^0.13.1
io: ^1.0.0 io: ^1.0.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request

View file

@ -1,5 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Updated `vm_service` to 11.6.0
## 7.0.1 ## 7.0.1
* Updated `server` header to `angel3` * Updated `server` header to `angel3`

View file

@ -17,8 +17,8 @@ In your `pubspec.yaml`:
```yaml ```yaml
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
angel3_hot: ^7.0.0 angel3_hot: ^8.0.0
``` ```
## Usage ## Usage

View file

@ -1,41 +1,41 @@
name: angel3_hot name: angel3_hot
version: 7.0.1 version: 8.0.0
description: Supports hot reloading/hot code push of Angel3 servers on file changes. description: Supports hot reloading/hot code push of Angel3 servers on file changes.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/hot repository: https://github.com/dukefirehawk/angel/tree/master/packages/hot
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
angel3_websocket: ^7.0.0 angel3_websocket: ^8.0.0
belatuk_html_builder: ^4.0.0 belatuk_html_builder: ^5.0.0
charcode: ^1.2.0 charcode: ^1.3.0
glob: ^2.0.1 glob: ^2.1.0
io: ^1.0.0 io: ^1.0.0
path: ^1.8.0 path: ^1.8.0
vm_service: ^9.3.0 vm_service: ^11.6.0
watcher: ^1.0.0 watcher: ^1.0.0
dev_dependencies: dev_dependencies:
http: ^0.13.2 http: ^1.0.0
logging: ^1.0.1 logging: ^1.2.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth
# angel3_client: angel3_client:
# path: ../client path: ../client
# angel3_websocket: angel3_websocket:
# path: ../websocket path: ../websocket

View file

@ -4,7 +4,7 @@ description: Support for rendering html_builder AST's as responses in Angel.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/angel3/packages/html_builder repository: https://github.com/dukefirehawk/angel/tree/angel3/packages/html_builder
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^7.0.0
belatuk_html_builder: ^4.0.0 belatuk_html_builder: ^4.0.0

View file

@ -1,6 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,9 +1,9 @@
name: angel3_http_exception name: angel3_http_exception
version: 7.0.0 version: 8.0.0
description: Exception class that can be serialized to JSON and serialized to clients. description: Exception class that can be serialized to JSON and serialized to clients.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/http_exception repository: https://github.com/dukefirehawk/angel/tree/master/packages/http_exception
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dev_dependencies: dev_dependencies:
lints: ^2.0.0 lints: ^2.1.0

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -13,7 +13,7 @@ In your `pubspec.yaml`:
```yaml ```yaml
dependencies: dependencies:
angel3_jael: ^6.0.0 angel3_jael: ^8.0.0
``` ```
## Usage ## Usage

View file

@ -22,7 +22,7 @@ AngelConfigurer jael(Directory viewsDirectory,
bool asDSX = false, bool asDSX = false,
bool minified = true, bool minified = true,
CodeBuffer Function()? createBuffer}) { CodeBuffer Function()? createBuffer}) {
var _cache = cache ?? <String, Document>{}; var localCache = cache ?? <String, Document>{};
var bufferFunc = createBuffer ?? () => CodeBuffer(); var bufferFunc = createBuffer ?? () => CodeBuffer();
@ -37,14 +37,14 @@ AngelConfigurer jael(Directory viewsDirectory,
//var stopwatch = Stopwatch()..start(); //var stopwatch = Stopwatch()..start();
if (cacheViews && _cache.containsKey(name)) { if (cacheViews && localCache.containsKey(name)) {
processed = _cache[name]; processed = localCache[name];
} else { } else {
processed = await _loadViewTemplate(viewsDirectory, name, processed = await _loadViewTemplate(viewsDirectory, name,
fileExtension: fileExtension, asDSX: asDSX, patch: patch); fileExtension: fileExtension, asDSX: asDSX, patch: patch);
if (cacheViews) { if (cacheViews) {
_cache[name] = processed!; localCache[name] = processed!;
} }
} }
//print('Time executed: ${stopwatch.elapsed.inMilliseconds}'); //print('Time executed: ${stopwatch.elapsed.inMilliseconds}');

View file

@ -1,47 +1,47 @@
name: angel3_jael name: angel3_jael
version: 7.0.0 version: 8.0.0
description: Angel support for the Jael templating engine, similar to Blade or Liquid. description: Angel support for the Jael templating engine, similar to Blade or Liquid.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/angel_jael repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/angel_jael
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
jael3: ^7.0.0 jael3: ^8.0.0
jael3_preprocessor: ^7.0.0 jael3_preprocessor: ^8.0.0
belatuk_code_buffer: ^4.0.0 belatuk_code_buffer: ^5.0.0
belatuk_symbol_table: ^4.0.0 belatuk_symbol_table: ^5.0.0
file: ^6.0.0 file: ^7.0.0
logging: ^1.0.1 logging: ^1.2.0
dev_dependencies: dev_dependencies:
angel3_test: ^7.0.0 angel3_test: ^8.0.0
html: ^0.15.0 html: ^0.15.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../../container/angel_container path: ../../container/angel_container
# angel3_framework: angel3_framework:
# path: ../../framework path: ../../framework
# angel3_http_exception: angel3_http_exception:
# path: ../../http_exception path: ../../http_exception
# angel3_model: angel3_model:
# path: ../../model path: ../../model
# angel3_route: angel3_route:
# path: ../../route path: ../../route
# angel3_mock_request: angel3_mock_request:
# path: ../../mock_request path: ../../mock_request
# angel3_auth: angel3_auth:
# path: ../../auth path: ../../auth
# angel3_client: angel3_client:
# path: ../../client path: ../../client
# angel3_websocket: angel3_websocket:
# path: ../../websocket path: ../../websocket
# angel3_validate: angel3_validate:
# path: ../../validate path: ../../validate
# angel3_test: angel3_test:
# path: ../../test path: ../../test
# jael3: jael3:
# path: ../jael path: ../jael
# jael3_preprocessor: jael3_preprocessor:
# path: ../jael_preprocessor path: ../jael_preprocessor

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -15,7 +15,7 @@ In your `pubspec.yaml`:
```yaml ```yaml
dependencies: dependencies:
jael3: ^6.0.0 jael3: ^8.0.0
``` ```
## API ## API

View file

@ -1,21 +1,21 @@
name: jael3 name: jael3
version: 7.0.0 version: 8.0.0
description: A simple server-side HTML templating engine for Dart. Comparable to Blade or Liquid. description: A simple server-side HTML templating engine for Dart. Comparable to Blade or Liquid.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/jael repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/jael
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
args: ^2.0.0 args: ^2.4.0
charcode: ^1.0.0 charcode: ^1.3.0
belatuk_code_buffer: ^4.0.0 belatuk_code_buffer: ^5.0.0
belatuk_symbol_table: ^4.0.0 belatuk_symbol_table: ^5.0.0
source_span: ^1.0.0 source_span: ^1.10.0
string_scanner: ^1.0.0 string_scanner: ^1.2.0
collection: ^1.15.0 collection: ^1.17.0
matcher: ^0.12.10 matcher: ^0.12.10
dev_dependencies: dev_dependencies:
lints: ^2.0.0 lints: ^2.1.0
test: ^1.21.0 test: ^1.24.0
executables: executables:
jaelfmt: jaelfmt jaelfmt: jaelfmt

View file

@ -108,7 +108,7 @@ void main() {
var buf = CodeBuffer(); var buf = CodeBuffer();
var document = jael.parseDocument(template, sourceUrl: 'test.jael')!; var document = jael.parseDocument(template, sourceUrl: 'test.jael')!;
var scope = SymbolTable<dynamic>(values: { var scope = SymbolTable<dynamic>(values: {
'starters': starters, 'starters': _starters,
}); });
const jael.Renderer().render(document, buf, scope); const jael.Renderer().render(document, buf, scope);
@ -153,7 +153,7 @@ void main() {
var buf = CodeBuffer(); var buf = CodeBuffer();
var document = jael.parseDocument(template, sourceUrl: 'test.jael')!; var document = jael.parseDocument(template, sourceUrl: 'test.jael')!;
var scope = SymbolTable<dynamic>(values: { var scope = SymbolTable<dynamic>(values: {
'starters': starters, 'starters': _starters,
}); });
const jael.Renderer().render(document, buf, scope); const jael.Renderer().render(document, buf, scope);
@ -338,7 +338,7 @@ void main() {
}); });
} }
const List<_Pokemon> starters = [ const List<_Pokemon> _starters = [
_Pokemon('Bulbasaur', 'Grass'), _Pokemon('Bulbasaur', 'Grass'),
_Pokemon('Charmander', 'Fire'), _Pokemon('Charmander', 'Fire'),
_Pokemon('Squirtle', 'Water'), _Pokemon('Squirtle', 'Water'),

View file

@ -7,8 +7,9 @@ class Analyzer extends Parser {
final Logger logger; final Logger logger;
Analyzer(Scanner scanner, this.logger) : super(scanner); Analyzer(Scanner scanner, this.logger) : super(scanner);
@override //@override
final errors = <JaelError>[]; //final errors = <JaelError>[];
SymbolTable<JaelObject>? _scope = SymbolTable<JaelObject>(); SymbolTable<JaelObject>? _scope = SymbolTable<JaelObject>();
var allDefinitions = <Variable<JaelObject>>[]; var allDefinitions = <Variable<JaelObject>>[];
@ -135,7 +136,6 @@ class Analyzer extends Parser {
return element; return element;
} finally { } finally {
_scope = _scope!.parent; _scope = _scope!.parent;
return null;
} }
} }

View file

@ -1,24 +1,26 @@
name: jael3_language_server name: jael3_language_server
version: 7.0.0 version: 8.0.0
description: Language Server Protocol implementation for the Jael templating engine. description: Language Server Protocol implementation for the Jael templating engine.
homepage: https://github.com/angel-dart/vscode homepage: https://github.com/angel-dart/vscode
publish_to: none publish_to: none
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
args: ^2.1.1 args: ^2.4.0
# dart_language_server: ^0.1.16 # dart_language_server: ^0.1.16
file: ^6.1.2 file: ^7.0.0
io: ^1.0.0 io: ^1.0.0
jael3: ^7.0.0 jael3: ^8.0.0
jael3_preprocessor: ^7.0.0 jael3_preprocessor: ^8.0.0
json_rpc_2: ^3.0.1 belatuk_symbol_table: ^5.0.0
logging: ^1.0.1 json_rpc_2: ^3.0.0
logging: ^1.2.0
path: ^1.8.0 path: ^1.8.0
source_span: ^1.8.1 source_span: ^1.10.0
string_scanner: ^1.1.0 string_scanner: ^1.2.0
belatuk_symbol_table: ^4.0.0 lints: ^2.1.0
lints: ^2.0.0 stream_channel: ^2.1.0
async: ^2.11.0
executables: executables:
jael3_language_server: jael3_language_server jael3_language_server: jael3_language_server
dependency_overrides: dependency_overrides:

View file

@ -1,5 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Updated `file` to 7.0.0
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -13,7 +13,7 @@ In your `pubspec.yaml`:
```yaml ```yaml
dependencies: dependencies:
jael3_prepreprocessor: ^6.0.0 jael3_prepreprocessor: ^8.0.0
``` ```
## Usage ## Usage

View file

@ -1,19 +1,19 @@
name: jael3_preprocessor name: jael3_preprocessor
version: 7.0.0 version: 8.0.0
description: A pre-processor for resolving blocks and includes within Jael templates. description: A pre-processor for resolving blocks and includes within Jael templates.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/jael_preprocessor repository: https://github.com/dukefirehawk/angel/tree/master/packages/jael/jael_preprocessor
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
file: ^6.1.0 file: ^7.0.0
jael3: ^7.0.0 jael3: ^8.0.0
belatuk_symbol_table: ^4.0.0 belatuk_symbol_table: ^5.0.0
collection: ^1.15.0 collection: ^1.17.0
dev_dependencies: dev_dependencies:
belatuk_code_buffer: ^4.0.0 belatuk_code_buffer: ^5.0.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# jael3: jael3:
# path: ../jael path: ../jael

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.1.1 ## 7.1.1
* Added `exclusive` parameter to `createSync` * Added `exclusive` parameter to `createSync`

View file

@ -5,3 +5,7 @@
Experimental virtual DOM/SPA engine built on Jael. Supports SSR. Experimental virtual DOM/SPA engine built on Jael. Supports SSR.
**Not ready for production use.** **Not ready for production use.**
## TODO
* Builder failed to generate the class

View file

@ -6,7 +6,7 @@ part of 'main.dart';
// JaelComponentGenerator // JaelComponentGenerator
// ************************************************************************** // **************************************************************************
abstract class _HelloJaelTemplate implements Component<dynamic> { mixin _HelloJaelTemplate implements Component<dynamic> {
DateTime get now; DateTime get now;
@override @override
DomNode render() { DomNode render() {

View file

@ -6,7 +6,7 @@ part of 'stateful.dart';
// JaelComponentGenerator // JaelComponentGenerator
// ************************************************************************** // **************************************************************************
abstract class _StatefulAppJaelTemplate implements Component<_AppState> { mixin _StatefulAppJaelTemplate implements Component<_AppState> {
//Timer? get _timer; //Timer? get _timer;
@override @override
void beforeDestroy(); void beforeDestroy();

View file

@ -6,7 +6,7 @@ part of 'using_components.dart';
// JaelComponentGenerator // JaelComponentGenerator
// ************************************************************************** // **************************************************************************
abstract class _MyAppJaelTemplate implements Component<dynamic> { mixin _MyAppJaelTemplate implements Component<dynamic> {
@override @override
DomNode render() { DomNode render() {
return h('div', {}, [ return h('div', {}, [
@ -16,7 +16,7 @@ abstract class _MyAppJaelTemplate implements Component<dynamic> {
} }
} }
abstract class _LabeledInputJaelTemplate implements Component<dynamic> { mixin _LabeledInputJaelTemplate implements Component<dynamic> {
String? get name; String? get name;
@override @override
DomNode render() { DomNode render() {

View file

@ -60,9 +60,8 @@ class JaelComponentGenerator extends GeneratorForAnnotation<Jael> {
} }
// Generate a _XJaelTemplate mixin class // Generate a _XJaelTemplate mixin class
var clazz = Class((b) { var clazz = Mixin((b) {
b b
..abstract = true
..name = '_${element.name}JaelTemplate' ..name = '_${element.name}JaelTemplate'
..implements.add(convertTypeReference(element.supertype)); ..implements.add(convertTypeReference(element.supertype));

View file

@ -1,23 +1,23 @@
name: jael3_web name: jael3_web
version: 7.1.1 version: 8.0.0
description: Experimental virtual DOM/SPA engine built on Jael3. Supports SSR. description: Experimental virtual DOM/SPA engine built on Jael3. Supports SSR.
publish_to: none publish_to: none
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
analyzer: ^5.0.0 analyzer: ^5.0.0
build: ^2.0.2 build: ^2.0.2
build_config: ^1.0.0 build_config: ^1.0.0
code_builder: ^4.0.0 code_builder: ^4.0.0
file: ^6.1.4 file: ^7.0.0
path: ^1.8.2 path: ^1.8.0
jael3: ^7.0.0 jael3: ^8.0.0
jael3_preprocessor: ^7.0.0 jael3_preprocessor: ^8.0.0
source_gen: ^1.0.2 source_gen: ^1.3.0
dev_dependencies: dev_dependencies:
build_runner: ^2.0.4 build_runner: ^2.4.0
build_web_compilers: ^3.0.0 build_web_compilers: ^4.0.0
lints: ^2.0.0 lints: ^2.1.0
dependency_overrides: dependency_overrides:
jael3: jael3:
path: ../jael path: ../jael

View file

@ -1,5 +1,10 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
* Update `jinja` to 0.4.2
## 7.0.0 ## 7.0.0
* Require Dart >= 2.17 * Require Dart >= 2.17

View file

@ -1,5 +1,6 @@
import 'package:angel3_framework/angel3_framework.dart'; import 'package:angel3_framework/angel3_framework.dart';
import 'package:jinja/jinja.dart'; import 'package:jinja/jinja.dart';
import 'package:jinja/loaders.dart';
/// Configures an Angel server to use Jinja2 to render templates. /// Configures an Angel server to use Jinja2 to render templates.
/// ///
@ -28,7 +29,7 @@ AngelConfigurer jinja({
createLoader ??= () { createLoader ??= () {
return FileSystemLoader( return FileSystemLoader(
extensions: ext, extensions: ext,
path: path, paths: [path],
followLinks: followLinks, followLinks: followLinks,
); );
}; };
@ -47,7 +48,7 @@ AngelConfigurer jinja({
); );
app.viewGenerator = (path, [values]) { app.viewGenerator = (path, [values]) {
return env.getTemplate(path).render.renderMap(values) as String; return env.getTemplate(path).render(values);
}; };
}; };
} }

View file

@ -1,37 +1,37 @@
name: angel3_jinja name: angel3_jinja
version: 7.0.0 version: 8.0.0
description: A service that renders Jinja2 template into HTML view for Angel3. Ported from Python to Dart. description: A service that renders Jinja2 template into HTML view for Angel3. Ported from Python to Dart.
homepage: https://github.com/dukefirehawk/angel/tree/master/packages/jinja homepage: https://github.com/dukefirehawk/angel/tree/master/packages/jinja
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
jinja: ^0.3.4 jinja: ^0.4.2
dev_dependencies: dev_dependencies:
angel3_test: ^7.0.0 angel3_test: ^8.0.0
path: ^1.8.0 path: ^1.8.0
test: ^1.21.0 test: ^1.24.0
lints: ^2.0.0 lints: ^2.1.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_test: angel3_test:
# path: ../test path: ../test
# angel3_websocket: angel3_websocket:
# path: ../websocket path: ../websocket
# angel3_client: angel3_client:
# path: ../client path: ../client
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth
# angel3_validate: angel3_validate:
# path: ../validate path: ../validate

View file

@ -1,38 +1,38 @@
name: angel3_markdown name: angel3_markdown
version: 7.0.0 version: 8.0.0
description: Angel3 Markdown view generator. Write static sites, with no build step. description: Angel3 Markdown view generator. Write static sites, with no build step.
homepage: https://angel3-framework.web.app/ homepage: https://angel3-framework.web.app/
repository: https://github.com/dukefirehawk/angel/tree/master/packages/markdown repository: https://github.com/dukefirehawk/angel/tree/master/packages/markdown
environment: environment:
sdk: '>=2.17.0 <3.0.0' sdk: '>=3.0.0 <4.0.0'
dependencies: dependencies:
angel3_framework: ^7.0.0 angel3_framework: ^8.0.0
file: ^6.1.2 file: ^7.0.0
markdown: ^6.0.0 markdown: ^7.1.0
dev_dependencies: dev_dependencies:
angel3_test: ^7.0.0 angel3_test: ^8.0.0
lints: ^2.0.0 lints: ^2.1.0
test: ^1.21.0 test: ^1.24.0
# dependency_overrides: dependency_overrides:
# angel3_container: angel3_container:
# path: ../container/angel_container path: ../container/angel_container
# angel3_framework: angel3_framework:
# path: ../framework path: ../framework
# angel3_http_exception: angel3_http_exception:
# path: ../http_exception path: ../http_exception
# angel3_model: angel3_model:
# path: ../model path: ../model
# angel3_route: angel3_route:
# path: ../route path: ../route
# angel3_mock_request: angel3_mock_request:
# path: ../mock_request path: ../mock_request
# angel3_test: angel3_test:
# path: ../test path: ../test
# angel3_websocket: angel3_websocket:
# path: ../websocket path: ../websocket
# angel3_client: angel3_client:
# path: ../client path: ../client
# angel3_auth: angel3_auth:
# path: ../auth path: ../auth
# angel3_validate: angel3_validate:
# path: ../validate path: ../validate

View file

@ -1,5 +1,9 @@
# Change Log # Change Log
## 8.0.0
* Require Dart >= 3.0
## 7.0.1 ## 7.0.1
* Fixed `BytesBuilder` warnings * Fixed `BytesBuilder` warnings

Some files were not shown because too many files have changed in this diff Show more