Introduction To DelphiMVCFramework
Introduction To DelphiMVCFramework
Daniele Teti
R&D Director & Educational
What is DelphiMVCFramework?
1
25/11/2013
• RESTful
– Richardson Maturity Model Level 3
• Designed with services and web client app in mind
• Server side generated pages using eLua (Embedded
Lua)
• Can be used in load balanced environment using
memcached (memcached.org)
• Fancy URL with parameter mappings
• Integrated Delphi RESTClient
• Messaging extension using STOMP
• Experimental support for IOCP
• Application Servers
• RESTful web services
• Classic web application
• Web Client Applications
• Messaging solutions
– based on Apache ActiveMQ or Apache Apollo
• Delphi thin clients
• Mobile and Web backends
• Scalable (Load balanced) web systems
• Secure servers with HTTPS
2
25/11/2013
DATABASE
3
25/11/2013
Request/Response Cycle
type
TWebModule1 = class(TWebModule)
procedure WebModuleCreate(Sender: TObject);
private
DMVC: TMVCEngine;
end;
. . .
procedure TWebModule1.WebModuleCreate(
Sender: TObject);
begin
DMVC := TMVCEngine.Create(self);
end;
4
25/11/2013
DMVCFramework
http://martinfowler.com/articles/richardsonMaturityModel.html
DelphiMVCFramework
5
25/11/2013
• One Application
• Many Controllers
– Classes inherited from TMVCController
• Many Actions for each controller
– Controller Actions are its methods instrumented with a
specific attribute
• Controller is addresses using a piece of URL
• Actions are selected using the second part of the URL
• One Application
• Many Controllers
– Classes inherited from TMVCController
• Many Actions for each controller
– Controller Actions are its methods instrumented with a
specific attribute
• Controller is addresses using a piece of URL
• Actions are selected using the second part of the URL
Server Name Controller Action
www.myserver.com/people/rome/danieleteti
6
25/11/2013
type
[MVCPath(‘/blog’)]
TBlog = class(TMVCController)
public
[MVCPath(‘/posts/($year)/($month)/($title)’)]
procedure GetArticle(CTX: TWebContext);
end;
DMVCFramework Attributes
7
25/11/2013
[MVCPath(‘/blog’)]
TBlog = class(TMVCController)
public
[MVCHttpMethod([httpGET])]
[MVCPath(‘/posts/($year)/($month)/($title)’)]
procedure GetArticle(CTX: TWebContext);
[MVCHttpMethod([httpPOST])]
[MVCPath(‘/posts/($year)/($month)/($title)’)]
procedure CreateArticle(CTX: TWebContext);
end;
[MVCPath(‘/blog’)]
TBlog = class(TMVCController)
public
[MVCHttpMethod([httpDelete])]
[MVCPath(‘/posts/($year)/($month)/($title)’)]
procedure DeleteArticle(CTX: TWebContext);
[MVCHttpMethod([httpPOST, httpPUT])]
[MVCPath(‘/posts/($year)/($month)/($title)’)]
procedure UpdateArticle(CTX: TWebContext);
end;
8
25/11/2013
[MVCPath(‘/blog’)]
TBlog = class(TMVCController)
public
[MVCProduce(‘application/json’, UTF8)]
[MVCHTTPMethod([httpGET])]
[MVCPath(‘/posts/($year)/($month)’)]
procedure GetArticleByMonth(
CTX: TWebContext);
end;
[MVCPath(‘/blog’)]
TBlog = class(TMVCController)
public
[MVCProduce(‘application/json’, UTF8)]
[MVCConsumes(‘application/json’)]
[MVCHTTPMethod([httpPOST])]
[MVCPath(‘/posts/($year)/($month)’)]
procedure CreateArticle(
CTX: TWebContext);
end;
9
25/11/2013
Request parameters
• Query String
– GET, POST, PUT, DELETE, HEAD, OPTIONS
• URL Mapped
– GET, POST, PUT, DELETE, HEAD, OPTIONS
• Request Body
– POST, PUT, OPTIONS
• Cookies
– GET, POST, PUT, DELETE, HEAD, OPTIONS
10
25/11/2013
Reading Parameters
Context.Request.Params[‘ParamName’]
11
25/11/2013
GET /blog/posts/danieleteti/2013/11
[MVCPath(‘/posts/($user)/($year)/($month)’)]
[MVCHTTPMethod([httpGET])]
procedure GetArticles (CTX: TWebContext);
. . .
procedure GetArticles (CTX: TWebContext);
var
year,month: Integer; user: String;
begin
user := CTX.Request.Params[‘user’];
year := CTX.Request.Params[‘year’].ToInteger;
month := CTX.Request.ParamsAsInteger[‘month’];
end
GET /blog/posts/danieleteti?year=2013&month=11
[MVCPath(‘/posts/($user)’)]
[MVCHTTPMethod([httpGET])]
procedure GetArticles (CTX: TWebContext);
. . .
procedure GetArticles (CTX: TWebContext);
var
year,month: Integer; user: String;
begin
user := CTX.Request.Params[‘user’];
year := CTX.Request.Params[‘year’].ToInteger;
month := CTX.Request.Params[‘month’].AsInteger;
end
12
25/11/2013
DEMO
• Routing
Renders
DMVCFramework
13
25/11/2013
Using Renders
Render a TObject
14
25/11/2013
Render a TJSONValue
Render a TDataSet
procedure TCustomersController.GetAll(
CTX: TWebContext);
var
wm: TWebModule1; //the main WebModule
begin
wm := GetCurrentWebModule as TWebModule1;
wm.qryCustomers.Open;
//dataset is rendered as json array of objects
Render(wm.qryCustomers);
end;
15
25/11/2013
DEMO
• Renders
• DEMO
– ActionsFilter
16
25/11/2013
• Server side views uses the Lua language just like PHP
pages use PHP (code into text)
• eLua (Embedded Lua) has been specifically designed
for DMVCFramework in its brother project called
LuaDelphiBinding
• It is similar to PHP for HTML, JSP for Java and erb for
Ruby
17
25/11/2013
Why Lua?
Is Lua popular?
• Lua is the most popular scripting language for game programming
• Adobe Photoshop Lightroom uses Lua for its user interface.
• Apache HTTP Server can use Lua anywhere in the request process
• Cisco uses Lua to implement Dynamic Access Policies within the Adaptive
Security Appliance.
• Damn Small Linux uses Lua to provide desktop-friendly interfaces
• FreePOPs, an extensible mail proxy, uses Lua to power its web front-end.
• MySQL Workbench uses Lua for its extensions & add-ons.
• Nginx has a powerful embedded Lua module that provides an API
• nmap network security scanner uses Lua as the basis for its scripting
language
• Vim has Lua scripting support
• VLC media player uses Lua to provide scripting support.
• Since March 2013, Lua is used as a new template scripting language on
Wikipedia and other Wikimedia Foundation wikis.
• WinGate proxy server allows event processing and policy to execute lua
scripts with access to internal WinGate objects.
• Wireshark network packet analyzer allows protocol dissectors and post-
dissector taps to be written in Lua
18
25/11/2013
19
25/11/2013
DEMO
• Simplewebapplication
20
25/11/2013
• WineCellarServer
• WineCellarServerWITHDORM
• AngularJS\WebClientSample
21
25/11/2013
Load Balancing
Messaging estensions
22
25/11/2013
• CallbackDemo
RESTClient
DMVCFramework
23
25/11/2013
RESTClient
var
rest: TRESTClient;
response: IRESTResponse;
Person: TPerson;
begin
rest := TRESTClient.Create('localhost', 3000);
response := rest.doGET('/people', ['1']);
Person := Mapper.
JSONObjectToObject<TPerson>(response.BodyAsJSONObject);
ShowMessage(Person.FullName);
Person.Free;
rest.Free;
end;
RESTClient Asynch
RESTClient.Asynch(
procedure(Response: IRESTResponse)
begin
//do something with response
end,
procedure(E: Exception)
begin
//do something with exception
end).
doPOST('/echo', [‘one', ‘two'],
‘Hello World’);
24
25/11/2013
RESTClient Asynch
RESTClient.Asynch(
procedure(Response: IRESTResponse) begin
//do something with response
end,
procedure(E: Exception) begin
//do something with exception
end,
procedure begin
//when finished (success or failure)
end).
doPOST('/echo', [‘one', ‘two'],
‘Hello World’);
DMVCFramework SubProjects
DMVCFramework
25
25/11/2013
Mapper
LuaDelphiBinding
26
25/11/2013
Thank You
Daniele Teti
[email protected]
www.danieleteti.it
@danieleteti
27