Professional Documents
Culture Documents
starter expert
COMPONENTS
DEVELOPERS 4
Delphi
In last issue of Blaise Pascal there was a great For now kbmMW supports AMQP v. 0.91
article by Fikret Hasovic, about AMQP (Advanced as a client fully, but in fact knows about all AMQP
Message Queue Protocol), explaining its structure 0.91 definitions so it potentially could also act as an
and some of the historical background about it. AMQP server.
This article is meant to follow up on that article, Components4Developers are considering also
by showing in praxis, how to install one of the supporting AMQP v. 1.0, which is actually in most
more famous AMQP servers (RabbitMQ), and
ways a subset of AMQP 0.91 but with a few changes
connect to it from a Delphi application using the
extensive middleware framework kbmMW
to the transport format. Please check the previous
Enterprise Edition. article by Fikret Hasovic to learn about the
differences between the two versions.
Preword
Some may pose the question if it isn't the case Installing RabbitMQ
that AMQP is a competitor to kbmMW's own Wide First step in anything to do with AMQP,
Information Bus. The short answer is yes: is to install an AMQP 0.91 aware server.
- Both frameworks have been designed for There are multiple to choose from, but one of the
distributing information from publishers to most popular ones, which is both fast and fairly easy
subscribers.
to use, is RabbitMQ.
- Both are built around temporary or persistent
queue based storage for the messages while For this example I only show how to install
they are in transit to the end subscriber. RabbitMQ on Windows. RabbitMQ is also running
- Both have been designed with performance and on Linux and other platforms.
stability in mind. As RabbitMQ is written using the Erlang language,
we need to install the Erlang runtime executables
However they also differ in areas: first.
- AMQP is 100% content agnostic. There is NO http://www.erlang.org/download.html
defined way or standard for how to interpret
Choose, depending on your Windows version, to
the contents of an AMQP message. It has to be
100% agreed between the sender and receiver. download either the 32 bit or 64 bit version of Erlang:
kbmMW have defined types of messages for
different purposes and with defined structure,
but also supports transferring generic content.
- AMQP is only a messaging framework. Nothing
more, nothing less. kbmMW WIB is the
messaging framework of kbmMW, but kbmMW
also contains an application server, database
connectivity, native JSON and XML stacks and
more, and is probably more comparable (in
functionality) to a combo of J2EE, Corba, RMI
and AMQP.
- AMQP is always doing copy/store of messages Run the downloaded file and install Erlang.
to relevant queues, while kbmMW supports
When installed, update your Windows system
reference counting when multiple endpoints
needs to receive a message. environment variables to include the variable
- AMQP natively builds on persistent named ERLANG_HOME.
queues, although it supports temporary queues It must point to the directory containing the Erlang
as well. kbmMW natively builds on shared bin directory.
in/out queues, and optional persistency in (Start > Settings > Control Panel > System >
named queues and thus avoids message Advanced > Environment Variables)
copying as much as possible.
So why AMQP?
Because AMQP is one of the only widely supported
methods of doing messaging between different
architectures and platforms.
As kbmMW is a swiss knife of features,
providing extensive connectivity for Delphi,
C++Builder and FreePascal, its only logical to also O
S
NT S
NE PER
4
P LO
M E
support AMQP as one of the many ways to integrate CO DEV
112 COMPONENTS
DEVELOPERS 4 Nr 5 / 6 2014 BLAISE PASCAL MAGAZINE
Having fun with Delphi and AMQP (Continuation 1)
COMPONENTS
DEVELOPERS 4
Now Erlang is ready for use.
Then download RabbitMQ from here:
http://www.rabbitmq.com
Click the download figure
If you are using Windows 8/8.1 without Classic Shell, you can instead
find the shortcuts on the Windows 8 application window.
As can be seen in the shortcuts, it's possible to start For the ease of use, RabbitMQ supports a
RabbitMQ as a service, which means it will stay management console which can be reached via
running after you log of your machine, which is how a Web browser, after having enabled it.
you will want it, the moment you use AMQP in a To do that, start the RabbitMQ command prompt
production environment. via the start menu in Windows.
Ports and numerous other configurations can be In the command prompt type:
made, either by defining a configuration file, or on rabbitmq-plugins enable
Windows by setting a number of environment rabbitmq_management
variables, before starting RabbitMQ. For now we will
run with the default configuration.
However you can read more about how to configure
it here
http://www.rabbitmq.com/configure.html.
114 COMPONENTS
DEVELOPERS 4 Nr 5 / 6 2014 BLAISE PASCAL MAGAZINE
Having fun with Delphi and AMQP (Continuation 3)
COMPONENTS
DEVELOPERS 4
Then start RabbitMQ, by installing it as a service via
the start menu. Start it, also via the start menu.
After it has been started, then RabbitMQ will be
listening on the default TCP port 5672. You can
check that by typing: netstat an | more
Somewhere in the list you will see
TCP 0.0.0.0:5672 if the RabbitMQ server has
been started using the default settings.
As we have enabled a management console, you will
also find RabbitMQ listening on TCP port 15672.
We can access that port via a web browser.
http://localhost:15672
The circled buttons and the TMemo are required for the sample, the remaining is optional.
116 COMPONENTS
DEVELOPERS 4 Nr 5 / 6 2014 BLAISE PASCAL MAGAZINE
Having fun with Delphi and AMQP (Continuation 5)
COMPONENTS
DEVELOPERS 4
The IP address can be changed to match the address In our case we simply update a counter, counting
of your RabbitMQ server (perhaps 127.0.0.1) if its how many messages we have received. We could
running on the same machine as your kbmMW also have extracted the received data (as the
AMQP client. commented code shows).
Next step is to declare at least one queue, which
Having a connection is great. will be used for temporary storage of data in the
However we also need to define a channel. AMQP server. The sample shows how to declare
What is a channel? multiple queues, and wait for acknowledgement
from the server that the queues has been formed. As
AMQP allows for multiple parallel streams of data
DeclareQueue is an async function, it will not wait
being passed via separate channels concurrently.
for the queue actually having been declared on the
At the same time the AMQP protocol guarantees that
server, however the kbmMW AMQP client does
messages pushed via a single channel is always sent
keep track of acknowledgements or failures from the
in the order that the data has been pushed. server when they turn up. By calling WaitAcks, the
You will normally want to have a channel per thread, client program stalls until all 3 queues have been
in a multithreaded environment, to ensure that your confirmed to be created on the server.
communication is running asynchronously. Even though a queue may already have been
So that's the reason for the Open channel button. declared and created by another AMQP client (or
Lets add some code for it. manually via the RabbitMQ management interface),
you still need to declare it in your own client. If the
private queue do not exist on the server, it will default be
FClient:TkbmMWAMQPClient; created. If it does exist, then it will be used as is, but
FChannel:IkbmMWAMQPChannel;
procedure only if you declare it with the exact same options (eg.
OnContent(Channel:IkbmMWAMQPChannel; mwaqoAutoDelete etc) as when the queue was
AContent:TkbmMWMemoryStream); declared first time. If it has been declared with
different options, then you will receive an error and
procedure TForm1.btnOpenChannelClick(Sender:
TObject);
be disconnected from the AMQP server.
begin In fact the AMQP protocol states that any error
FChannel:=FClient.OpenChannel; happening due to wrong/illegal request from an
FChannel.OnContent:=OnContent; AMQP client MUST result in disconnection from the
end;
server, immediately after the server have sent an
procedure TForm1.btnCloseChannelClick(Sender: asynchronous notice about the reason. It can be
TObject); handy to look in the RabbitMQ log directory to check
begin up on reasons for disconnections, if you do not
FClient.CloseChannel(FChannel);
end;
understand why you are being disconnected.
procedure private
TForm1.OnContent(Channel:IkbmMWAMQPChannel; { Private declarations }
AContent:TkbmMWMemoryStream); FClient:TkbmMWAMQPClient;
//var // s:string; FChannel:IkbmMWAMQPChannel;
begin FQueue1,
// The following will be executed in a thread, and should FQueue2,
// thus be synchronized to be threadsafe. FQueue3:IkbmMWAMQPQueue;
// However for simplicity of the sample procedure
OnContent(Channel:IkbmMWAMQPChannel;
//we don't do this now.
AContent:TkbmMWMemoryStream);
// However NEVER run code in production that updates
// the GUI from another thread without using
procedure TForm1.btnDeclareNamedQueueClick(
//Synchronize because it WILL fail! Sender: TObject);
// s := TkbmMWPlatformMarshal.UTF8Decode( begin
// AContent.Memory,AContent.Size); FQueue1:=FClient.DeclareQueue(
// mLog.Lines.Add( FChannel,'QUEUE1',[mwaqoAutoDelete]);
//'Got'+ IntToStr(AContent.Size) FQueue2:=FClient.DeclareQueue(
// +' Bytes of content: '+ s); FChannel,'QUEUE2',[mwaqoAutoDelete]);
FQueue3:=FClient.DeclareQueue(
TkbmMWInterlocked.Increment(FReceived); FChannel,'QUEUE3',[mwaqoAutoDelete]);
end; FChannel.WaitAcks;
end;
COMPONENTS
DEVELOPERS 4 Specialist help and consultancy
for kbmMW
- Added AMQP 0.91 client side gateway Supports Delphi/C++Builder/RAD Studio 2009
support and sample. to XE7 (32 bit, 64 bit and OSX where applicable).
- Updated StreamSec TLS transport plugin kbmMW for XE5 to XE7 includes full support for
component (by StreamSec). Android and IOS (client and server).!
- Improved performance on Indy TCP/IP
kbmMemTable is the fastest and most feature rich
Client messaging transport for large number in memory table for Embarcadero products.
of inbound messages.
- Easily supports large datasets
- Native high performance 100% developer with millions of records
defined application server with support for - Easy data streaming support
loadbalancing and failover - Optional to use native SQL engine
- Native high performance JSON and XML - Supports nested transactions and undo
- Native and fast build in M/D,
(DOM and SAX) for easy integration with
aggregation /grouping,
external systems range selection features
- Native support for RTTI assisted object - Advanced indexing features for
marshalling to and from XML/JSON, now also extreme performance
with new fullfeatured XML schema
(XSD) import Warning!
- High speed, unified database access kbmMemTable and kbmMW
(35+ supported database APIs) with
connection pooling, metadata and
are highly addictive!
Once used, and you are hooked for life!
data caching on all tiers
- Multi head access to the application server,
via AJAX, native binary, Publish/Subscribe,
SOAP, XML, RTMP from web browsers,
embedded devices, linked application
servers, PCs, mobile devices, Java systems
and many more clients
- Full FastCGI hosting support.
Host PHP/Ruby/Perl/Python applications in
kbmMW!
COMPONENTS
DEVELOPERS 4
EESB, SOA,MoM, EAI TOOLS FOR INTELLIGENT SOLUTIONS. kbmMW IS THE PREMIERE N-TIER PRODUCT FOR DELPHI /
C++BUILDER BDS DEVELOPMENT FRAMEWORK FOR WIN 32 / 64, .NET AND LINUX WITH CLIENTS RESIDING ON WIN32 / 64,
.NET, LINUX, UNIX MAINFRAMES, MINIS, EMBEDDED DEVICES, SMART PHONES AND TABLETS.