What is the best way to do application data exchange in Delphi without sockets? - delphi

I need a few of my related applications to communicate to each other (exchange data and initiate actions). Requirements are without packages and no sockets. So I guess that leaves named pipes, WM_CopyData (like Skype does it) and command parameters. What are your best practices?

You probably have a couple of options.
Beyond what you already have:
DDE
Memory Mapped Files (MMF)
MailSlots
I would probably go with either the Pipes or the MMF.
There are a couple of free MMF components that you can download,
Deborah Pate has a set of freeware classes you can use.
MapFiles.zip
Check for MailSlots on Torry's site.
The final solution might be dependent on the amount, size and frequency of the data transfers that decide which option you choose.

I would advise to use COM in this situation. (Attention: not COM+, not ActiveX, not OLE; COM, just COM.)
Since Delphi 7 (or an earlier version, I'm not sure), this is easily done by adding a Type Library to the project, and an Automation object.
Advantages are it's pretty widely supported, both within Delphi (the Type Library Editor has everything you need and updates your code, and COM internals and registering are catered for from the ComServ unit), and outside of Delphi (I use it in a number of project to interact with all sorts of applications: C++ projects, Word and Excel documents using VBA, oldskool ASP...).
An only disadvantage I encountered may be threading issues, in normal applications, a plain CoInitialize(nil); at application startup will do, in more complex applications, you need to think about 'threading apartments' or use free threading and do your own locking. (Which in some cases you've been doing already.)

Another alternative which is dirt simple to implement is to use the database to pass information.
Not overly elegant, and it does use a lot of overhead, but if your application is already data-aware (ie has a database as part of it), then using a table or two to pass information is pretty easy.

You could use simple files: One side writes to it, the other reads. If you need two way communication, just use two files, one for each direction.
Of course this is not really high performance.

Another vote from me for named pipes, for the data exchange. I like them slightly more than mmap files, since the win32 pipe APIs give you some nice choices out of the box: sync/async, byte stream vs message packets, simple ReadFile/WriteFile calls. All of which you could do yourself with mmaps... but pipes are already there...
And you can control access with security attributes -- which isn't an option with WM_CopyData. This might not be an issue immediately... but can be handy to have the option, even if you don't care who sends your app messages. For me, this was helpful when Vista came along, and suddenly user apps ran in a separate session to my service. Was good that tweaking the security attributes was the only thing needed to get things working again.
For "initiating actions", you might be able to get away with something as easy as some named Events, and not worry about sending messages at all? The interested parties simply wait for it to be signalled.
Personally, I'd avoid COM unless you have to specifically support COM-based clients.

Do not use COM, too much overhead (variants) and you must register you .dll or .exe (and it gives a lot of weird installation + update problems).
I should go for MMF, I use this for communication with Windows Services.
I use the following TGpMessageQueueReader and writer for this:
http://17slon.com/gp/gp/gpsync.htm

If you want to pass data, call functions etc then use COM, however if there are lots of calls be aware that COM is slow. Also you might have to register the application with "xxx.exe /Regserver", before it will work.

Is'nt this the sort of this that RemObjects is good at?
Bri

Related

Stringgrid content in other application

Heading : How can I read a StringGrid content in another application's window?
I could get the StringGrid's handle
A Delphi string grid is a pure VCL control. You cannot use windows messages to read its content. You cannot use any of the automation APIs because Embarcadero do not and have never made their controls accessible. For which, incidentally, shame on them.
The only viable way to do this is through gross hacking. If you know the memory layout of the control you can read its memory the same way as a debugger does. Using calls to ReadProcessMemory. However, this will be exceptionally messy and hard to achieve.
A simple approach would be to inject a DLL into the target process. So long as your DLL is built with the same version of Delphi as the target process, there's a reasonable chance that you'll be able to read out the contents of the grid. You can then use IPC to send the information back to the other program.
Note that none of these solutions are remotely appealing. If you can find a cleaner way to do this, possibly avoiding this target process altogether, then you should give it strong consideration.

Changes to make in Delphi source library so as the resulting .dll is recognized as a different dll when registered in windows

I have the source in delphi of an open source electrical solver (OpenDSS)
Normally, when installing OpenDSS, the engine is registered as a COM component.
I want to compile the engine 8 times making 8 differente dll's that internally are exactly the same. Why? because I want to use 8 mono-core solvers at once to perform monte carlo simulations.
The problem is that by simply renaming the dll's and registering them, windows recognize them as the same COM component. So the question is; What changes shall I make in the source so when I compile the library I cheat windows?
I hope que question is clear enough, and thank you in advance.
Naively, the answer to your question is to make eight different versions of the code that are identical apart from having different CLSIDs. Keep all the IIDS of the exposed interfaces the same, but vary the CLSIDs. That allows you to register eight distinct COM servers with different CLSIDs to identify them. But you request the same IID from each COM object that you create.
This is a pretty vile solution though. It doesn't scale very well. It's expensive of memory. It's just really unwieldy. It would surely be possible to make the code threadsafe. Usually this can be done by locating the globals and dealing with them. Typically by converting them into parameters or state.
If you cannot manage that then you could create a stub executable to allow the server to run out-of-proc. Then instantiate separate instances of the out-of-proc server.

Delphi Application over the web

Possible Duplicate:
What Web Application Framework for Delphi is recommended?
We have a Delphi 2007 desktop application which we have hosted using Citrix. Now we want to get rid of Citrix and somehow web-enable it.
I have done bit of research and found that it is possible by using the uniGUI.
http://www.unigui.com
Conclusion: Can be done, but would require a re-write and only a subset of components are supported. Serious questions remain are the monolithic application structure in a web environment.
There are two more options morfik and atozed and they also require a re-write.
I want to know if there is any other option which requires a very less re-write work and how fragile is it?
How fragile it is, is based on the quality of your code. If you have a good structured application, with business logic and data access fully separated from the GUI, it will be pretty safe, although you still have to rewrite mostly all your GUI.
If there's logic in your forms, and the code that talks to the GUI components is intwined with the code that checks your input and stores the data, then you have a big problem.
In that case, this is a great opportunity to refactor large portions of your app and do it better this time. ;)
Since there is no "silver bullet" here, it doesn't matter much which product you use. You have the same challenges with any of them. I would recommend spending a few days on a Proof-of-Concept (PoC) re-write of 2-3 typical screens. Implement the POC for each "finalist" product, and see how it works out. Keep track of how long it took for each one, things that were easier/harder, and how the end result appears to the end-user (performance, good/funny-looking, robustness, "feel").
As for the actual re-write, I would recommend the following:
Re-factor existing application to remove business logic from the UI.
Full Regression testing, and push that into production.
NOW proceed with conversion to one of the web tools.
Oops - I left out a step. Step 0: FREEZE all features/fixes. If fixes are needed to current production, they'll need to be done in a separate branch, and then rolled-up into this project later.
Note that this type of work lends itself nicely to outsourcing, as the work is straightforward and the requirements are simple. Especially if it can be delivered one form at a time, so progress, timelines, and $$$ can be measured in small chunks.
Another preliminary step is to develop a "cook book" for stripping the business logic from the existing GUI layer. It should identify naming conventions, common libraries (for code that should have been shared all along but wasn't), and should describe the conversion methodology.
AFAIK, there's not tool will convert your desktop application to web application without requiring rewrite for most of GUI Parts.
as Golez said, you will have to refactor your application, try to separate your business logic from the GUI, then you can use some tools like Intraweb to develop the GUI as web and reusing the existing business logic with it.
Another option by converting your application to n-tiers technology and warp your business logic as web services or any open technology and make your web part by any web languages such as ASP.Net or PHP.
Depending on how 'Web enabled' you want the App to be.. I use Cybele Software's (https://www.cybelesoft.com/) Thinfinity UI to extend Apps to the Web, including Database Apps.
It only requires the installation of their ThinFinity Server and one line of code added to the Proj source and you are in business.
The Apps all run on your PC.
Well perhaps I simplified it a little, but worth a look.
HTH.
Regards,
Ian

What elements are needed to implement a remote, event driven system? - overview needed

I am trying to design an event driven system where the elements of the system communicate by generating events that are responded to by other components of the system. It is intended that the components be independent of each other - or as largely independent as I can make them. The system will initially be implemented on Windows 7, and is being written in Delphi. The generated events will be generated by the Delphi code. I understand how to implement a system of the type described on a single machine.
I wish to design the system so that it can readily be deployed on different machine architectures in particular with different components running on a distributed architecture, which may well be different to Windows 7. There is no requirement for the system ever to communicate with any systems external to itself.
I have tried investigating the architecture I need to consider and have looked at the questions mentioned below. These seem to point towards utilising named pipes as a mechanism for inter-hardware communications. As a result of these investigations I have sketched out the following to describe my system - the first part of the diagram is the system as I am developing it; the second part what I have deduced I would need for possible future implementations.
This leads to the following points:
Can you pass events via named pipes?
Is this an appropriate and sensible structure to tackle this problem?
Are there better alternatives?
What have I forgotten (at this level of granularity)?
How is event driven programming implemented?
How do I send a string from one instance of my Delphi program to another?
EDIT:
I had not given the points arising from "#I give crap answers" response sufficient consideration. My initial responses to his points are:
Synchronous v Asynchronous - mostly asynchronous
Events will always be in a FIFO queue.
Connection loss - is not terribly important - I can afford to deal with this non-rigourously.
Unbounded queues are a perfectly good way of dealing with events passed (if they can be) - there is no expectation of large volume of event generation.
For maximum deployment flexibility (operating-system independent), I recommend to take a look at popular open source message brokers which run on the Java platform. Using standard protocols. they integrate well with Delphi and other programming languages, can be used with web applications, and have a large installed user base and active community.
They are quite easy to install and configure in a few minutes, and free / commercial clients for Delphi are available.
Some examples are:
Apache ActiveMQ
OpenMQ
JBoss HornetQ
I also recommend the book "Enterprise Integration Patterns" by Martin Fowler as an overview and introduction, with many simple recipes to handle specific problems.
Note that I am a developer of commercial Delphi clients for enterprise messaging systems, such as xmlBlaster, RabbitMQ, Amazon Simple Queue Service and the three brokers mentioned above.
I can only answer for your point 4 here: You have not yet decided if an event is synchronous or asynchronous. In the async case, you have to decide what to do when messages arrive. Do you have a queue? How big is the queue? Can one grab arbitrary elements in the queue or is it strictly FIFO. What happens if a message is lost (somebody axes the network cable)?
In the sync variant, the advantage is that you got delivery guarantees, but then what do you do when connections are suddenly lost?
Connection loss is going to be a problem. The more machines you have, the greater is the chance that they will occur. Decide how you will handle that.
Another trouble may be what you do if you have a large event and several small. Is the order of transfer FIFO or smallest-first? Can events be reeordered? What are the assumptions here?
The aside is that I hack Erlang a lot. In Erlang all the event-handling is already solved but it also means a specific model is chosen for you (async, unbounded queues, no guaranteed delivery, but detection of connection loss).
I suggest to look at RabbitMQ, http://www.rabbitmq.com/. It has the server and client. Just need some wrapper codes in delphi and you are ready to build your business logic
Cheers
This is probably just an application for a message queue.
http://msdn.microsoft.com/en-us/library/ms632590(v=vs.85).aspx

How to add code inside a program in runtime (Delphi/Windows)?

I'm working on Windows XP/Delphi 7. I need to add some procedures (or functions) inside a program that is running, and I do not want to re-compile it once again after I finished it.
I just have a host application with 5 functions to send different types of alarms, but there are other new alarm types, so I have to do new functions to send those alarms, but I should not re-build the host application. I have a class named TAlarmManager that it's invoked calling those functions.
Maybe a plugin?? OK, but how can I "insert" new functions??? Tutorial, manual, book, etc.. for learning about this, or any advice on how to do this???
I have studied plugins (I'm totally new on this theme), but no one "talks" about adding functions to a host application. It seems to me that plugins add functionality from itself, I mean, they have been developed with self code to do something, not to "add" code to the host application... How can I do this??
For the technical side: How does the Delphi IDE do it? That would be the first place for me to look.
To understand plugins, you must understand that you can't add new functions. You could but since the old code doesn't know how to call it, they wouldn't be called.
So what you do is you add a "register" or "start" function to your plugin. That start function gets a data structure as parameter which it can examine or extend. In your case, that would be the list of alarms. Alarms always work the same (my guess), so it can add additional alarms.
The main code will then, after registering all plugins, just walk over the list of alarms and invoke the standard alarm function on each of them. It no longer cares where each alarm comes from and what it really does.
The key here: You need to define an interface which both sides subscribe to. The main code calls the interface functions and your plugin code implements them.
Another option available is to use a scripting component to your project. One which works quite well is PascalScript. This would allow you to load external scripts after the fact and then run them as needed to interact with your application. As Aaron suggested you will also need to still provide an interface of some sort for your script to interact with your application.
See also Plugins system for Delphi application - bpl vs dll? here on Stackoverflow.
I'm not quite sure what you mean by "alarms", so I'm making a couple of assumptions.
1) If you don't need additional code for the alarms, I would try to make them data driven. Keep the different kinds of alarms in a database or configuration file, which makes it easy to update applications in the field without recompiling or reinstalling.
2) If you need special code for each alarm, you could use run time packages as plug-ins for your application. Search for Delphi runtime packages to get some ideas and tutorials. Here are a couple of links I found:
http://delphi.wikia.com/wiki/Creating_Packages
http://delphi.about.com/od/objectpascalide/a/bpl_vs_dll.htm
3) Scripting, as skamradt already mentioned. If it makes sense for your application, this could also let your customers write their own add-on functionality without requiring a recompile on your part.
You almost definitely want to use Pascalscript, as skamradt suggests. You should start here, and seriously consider this option. There are many possibilities that come out of being able to serialize live code as text. The only downside is possibly speed of execution, but that may not matter for your application domain. I would have upvoted skamradt, but I don't have enough reputation to upvote :)
Some time ago I was looking at a situation sort of like what you're describing.
My answer was .DLLs. I put the variable code in a .DLL that was dynamically loaded, the name specified in a configuration file. I passed in a record containing everything I knew about the situation.
In my case there was only a success/fail return and no screen output, this worked quite well. (It was commanding a piece of machinery.)
This sounds like a place where a scripting language or "Domain Specific Language" may make sense. There are several approaches to this:
Implement alarm functions in VBscript (.vbs files written in notepad) that accesses your Delphi code via COM API. Using the COM API gives you access to a large range of programming tools for writing functions, including Delphi. This is the most clumsy solution, but easiest to do. It may also be a benefit to your sales process, and it is always good to think about how to sell things.
Implement your own function language in Delphi. This way you can make it so easy, that your endusers can write their own alarm functions. If you do it as an expression evaluator, you can write an alarm as 2*T1>T2. There are several expression evaluators out there, and you can also write your own if they don't match your needs.
Use a predefined programming language inside your Delphi application, for instance, "Pascal Script", see http://www.remobjects.com/ps.aspx
You should take a look at PaxCompiler, like PascalScript it allows to load scripts, but you can even precompile them before for more performance. Look at the demos section for the solution of your problem.
As a side note, the web page really looks bad, but the package is really powerful and stable.
I think that the scripting solution it's good for this situation.
There are many scripting packages that you can evaluate:
Context Scripting Suite
Fast Script
RemObjects Pascal Script
TMS Scripter Studio
paxScript
Other packages that you can find on Torry, DSP, VClComponents,...
Regards.

Resources