-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathapplication.js
139 lines (117 loc) · 3.54 KB
/
application.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
import * as path from "https://deno.land/std/path/mod.ts";
import * as log from "https://deno.land/std/log/mod.ts";
import { Application as Oak } from "https://deno.land/x/oak/mod.ts";
import Routes from "./routes.js";
import Database from "./application/database.js";
import Cache from "./application/cache.js";
import DEFAULTS from "./application/defaults.js";
import Token from "./application/token.js";
import EnvironmentConfig from "./application/initializers/environment-config.js";
import DefaultMiddleware from "./application/initializers/default-middleware.js";
import SetupAssets from "./application/initializers/setup-assets.js";
import MissingRoute from "./application/middleware/missing-route.js";
export default class Application {
constructor(config = {}) {
this.config = { ...DEFAULTS, ...config };
this.oak = new Oak();
this.routes = new Routes(this);
this.root = path.dirname(this.config.root || Deno.cwd());
this.initializers = [];
this.plugins = [];
this.setup();
}
/**
* Run the code given in the callback when the app initializes.
*/
initializer(Initializer) {
this.initializers.push(Initializer);
}
/**
* Add routes, initializers, and configuration from a plugin.
*/
include(plugin) {
this.plugins.push(plugin);
}
/**
* Append an application middleware function to the Oak stack.
* Application middleware functions apply an additional argument, the
* current instance of the application.
*/
use(middleware) {
const appified = (context, next) => middleware(context, next, this);
this.oak.use(appified);
}
/**
* Run immediately after instantiation, this is responsible for
* setting up the list of default initializers prior to any other
* initializers getting loaded.
*/
setup() {
this.initializer(EnvironmentConfig);
this.initializer(DefaultMiddleware);
this.initializer(SetupAssets);
}
/**
* Run all initializers for the application.
*/
async initialize() {
this.log = await this._setupLogging();
this.log.info("Initializing Saur application");
this.plugins.forEach((plugin) => plugin.initialize(this));
this.initializers.forEach(async (init) => {
await init(this);
});
}
deliver(Mailer, action, ...options) {
return Mailer.deliver(this, action, ...options);
}
/**
* Apply routing and start the application server.
*/
async start() {
this.oak.use(this.routes.all);
this.oak.use(this.routes.methods);
this.use(MissingRoute);
this.log.info(
`Starting application server on port ${this.config.server.port}`,
);
await this.oak.listen(this.config.server);
}
/**
* Authenticity token for the current time and secret key base.
*/
get authenticityToken() {
return new Token(new Date(), this.config.authenticity);
}
/**
* Database connection for the application.
*/
get db() {
const Adapter = Database.adapt(this.config.db.adapter);
return new Adapter(this.config.db, this.log);
}
/**
* Cache database connection for the application.
*/
get cache() {
const Adapter = Cache.adapt(this.config.cache.adapter);
return new Adapter(this.config.cache, this.log);
}
async _setupLogging() {
const {
log: { level, formatter },
} = this.config;
await log.setup({
handlers: {
default: new log.handlers.ConsoleHandler(level, { formatter }),
},
loggers: {
default: {
level: level,
handlers: ["default"],
},
},
});
return log.getLogger();
}
}