AOP support in Delphi - delphi

Is it possible to do Aspect Oriented Programming in Delphi? I would be interested in native support as well as third party solutions.
I don't have a specific problem I want to solve with AOP, but am simply interested in studying AOP.

AOP depends on two things:
The ability to inject additional code into an existing unit of code
A mechanism to place conditions on where code should be injected.
This is commonly referred to as code weaving. It is a specialization within the larger study of program transformation.
JIT compiled languages have more options for implementing code weaving than statically compiled programs because more information is retained in the bytecode/IL. They also support reflection, which offers the ability to manipulate code at runtime.
Delphi.NET and Prism have the same access to these capabilities as any other .NET language.
There are two AOP frameworks for Delphi Win32 that I'm aware of. The first is MeAOP, which has already been mentioned. The second is Infra. Both projects take a similar approach to AOP. They use a combination of RTTI and clever pointer manipulation to intercept method calls so you can run additional code before or after the method call. You define your cross-cutting feature as a subclass of the framework's AOP class. You register the methods you want intercepted by passing the method name as a string argument to the AOP framework.
Both frameworks are still actively developed and are actually larger in scope than just AOP. Unfortunately documentation is somewhat sparse (and in Infra's case mostly in Portuguese)
Another project attempted AOP through source code weaving back in 2004 with some success. Basically they built an aspect weaver on top of a general purpose program transformation tool called DMS and used it to inject code into delphi source files prior to compilation. Their aspect oriented language was primarily influenced by AspectJ.
http://www.gray-area.org/Research/GenAWeave/ has links to the original paper and presentation as well as some videos of the transformation process.
It may also be possible to use runtime code instrumentation to accomplish this as well. Its a technique used by some profilers to inject counters and stack traces into running code without modifying the original source. A similar technique could be used to inject crosscutting concerns into a statically compiled executable. The PinTool project is a good example of this.

ClassHelpers in the later versions of Delphi allow some very limited level of AOP type behavior. You can use ClassHelpers to inject behavior into other classes without descending from them. It allows overriding existing methods and then optionally calling that existing method.
The limitation is you must declare a ClassHelper for a specific class and it descendants. Additionally a class can only have one ClassHelper.
These are similar to Extension methods in C#.

The DSharp library features AOP:
https://bitbucket.org/sglienke/dsharp
More info can be found at: https://bitbucket.org/sglienke/dsharp
Also have a look at TVirtualMethodInterceptor.
It's in the RTL since Delphi 2010 and allows you to do OnBefore, OnAfter, etc. calls on all virtual methods on a class.
This call alone should cover must of what you need using Rtti, not weaving which is much faster than run-time weaving.

Related

Accessing classes that are in another DLL?

Is there is a way of exporting and using classes from another dll,
I have 2 dll's and I am trying to access classes in between, was wondering if this is possible.
There are a variety of ways to achieve this, including but not limited to the following:
Use runtime packages rather than DLLs. Then you can use any types, variables, etc. from another module. Note that this forces you to use runtime packages in all of your modules, and to compile all of the modules with the same version of Delphi.
Continue to use DLLs, but access the types via interfaces rather than Delphi classes. Interfaces, unlike classes, can be exported across DLL boundaries.
Continue to use DLLs, but access the types using unit scope procedures and functions rather than classes. This would lead you to an interface of the same nature as the Win32 interface.
Of the above options, they are arranged in order of decreasing convenience. The most convenient is to use runtime packages but that may place an undesirable constraint on you that all modules are compiled with the same Delphi version. Interfaces are usually more convenient to consume than a Win32 style interface, but there may be more programming overhead in setting up such an architecture. You'll have to make the choice that you feel best suits your needs.
If you can avoid using separate modules in the first place, and build everything into a single executable file, then that is far and away the most convenient approach.

Why AOP and DI aren't used together very often

I am confused about this line
Aspect-Oriented Programming and Dependency Injection are very different concepts, but there are limited cases where they fit well together.
from this website
http://www.postsharp.net/blog/post/Aspect-Oriented-Programming-vs-Dependency-Injection
I understand the advantages of DI over AOP, but why aren't they used together more often? why are there only limited cases where they fit together? Is it because of the way AOP is compiled, that makes using both difficult?
How do you define "limited cases"? I myself always use AOP and DI together.
There are basically three ways to apply AOP, which are:
Using code weaving tools such as PostSharp.
Using dynamic interception tools such as Castle Dynamic Proxy.
Using decorators.
The use of DI with code weaving tools doesn't mix and match very well, and I think that's the reason that the Postsharp site states that "there are limited cases where they fit well together". One reason it doesn't mix and match is because Dependency Injection is about loose coupling, while code weaving hard couples your code and the aspects together at compile time. From a perspective of DI, code weaving becomes an anti-pattern. In section 11.2 of our book, Mark and I make this argument very clear. In summary we state:
The aim of DI is to manage Volatile Dependencies by introducing Seams into your application. Theis enables you to centralize the composition of your object graphs inside the Composition Root.
This is the complete opposite of hat you achieve when applying compile-time weaving: is causes Volatile Dependencies to be coupled to your code at compile-time. This makes it impossible to use proper DI techniques and to safely compose complete object graphs in the application's Composition Root. It's for this reason that we say that compile-time weaving is the opposite of DIā€“using compile-time weaving on Volatile Dependencies is an anti-pattern. [page 355]
If you use dynamic interception, however, which means applying cross-cutting concerns at runtime by generating decorators on the fly it works great with DI and it is integrated easily with most DI libraries out there, and can be done as well when using Pure DI, which is something we demonstrate in section 11.1.
My personal preference is to use decorators. My systems are designed around a few well defined generic abstractions, and this allows me to apply cross-cutting concerns at almost all places that are important to my system. That leaves me in very rare cases with a few spots where decorators don't work very well, but this is almost always caused by design flaws. Either by my own limitations as a developer or by design flaws in the .NET framework or some other tool. One famous design flaw is the INotifyPropertyChanged interface. You might have guessed it, but in our book we describe this method in a lot of detail. We spend a complete chapter (10) on this topic.

Does Swift support aspect oriented programming?

I am an iOS developer trying to learn aspect oriented programming but does Swift support aspect oriented programming?
The foundation of Aspect Oriented Programming is the intercept pattern. We start with a crosscutting requirement - something that needs to occur in many parts of the application. And then using a pointcut expression, modularize it, by identifying all of the places this requirement should be applied. This is done by intercepting a method call and weaving in additional behavior. Therefore, for a language to support AOP, it must support the intercept pattern.
Now, depending on the language, method interception can be applied either at compile-time, run-time or both. Swift is an interesting case in this regard, as it supports the following kinds of method dispatch:
Static/vtable, like C++ (faster : in tests accounted for about 1.1 nano-seconds or less of method invocation time)
Messaging, like Objective-C (slower : in tests accounted for about 4.9 nano-seconds of method invocation time). Also known as dynamic dispatch or late binding.
If you extend NSObject or use the #objc decoration then messaging will be used. Otherwise Swift will revert to static/vtable method invocations.
With the static/vtable type of dispatch, only compile-time interception is possible. In the case of C++ (and Swift) this involves using a preprocessor that generates new source, prior to actual compilation. This is a somewhat cumbersome approach and takes more effort to develop the necessary tools. Although it does give the best possible performance.
With the messaging style of method invocation run-time interception is also available. In fact, Objective-C made interception so easy that there was no formal AOP framework. It might've been useful, but "raw materials" were so good no one bothered to make one. Many of Cooca's best features take advantage of Objective-C's dynamic dispatch and the ability to intercept method calls.
Summary:
Swift will support runtime AOP if you extend NSObject or use the '#objc' decoration. There are some quirks and limitations to this - Apple's guide on using KVO with Swift will point out most of them.
If you don't extend an Objective-C base or use the '#objc' decoration, then only compile-time AOP will be possible. As yet there is no such library to provide compile-time AOP. Furthermore, a disadvantage of compile-time AOP is that it only works with classes that you have the source for.
NB1: Some languages, such as Java uses a static/vtable style of method dispatch and still support runtime method interception. This is possible as they rely on virtual machine, along with a class loader, another hook-in point. In fact Java is still classed as a 'late binding' language because of this.
NB2: Its technically possible to support provide compile time weaving against compiled-to-machine-code binaries with some limitations. The first is there aren't too many tools to support this because implementation effort is high, and must be repeated per-platform. The second is that it limits the available AOP features.
Unfortunately, Swift itself has no runtime support at this time. You have to rely on Objective-C bridging.
Here's a brand new AOP library for iOS, written in Objective-C, with Swift support.
https://github.com/MO-AI/MOAspects
Only 'before advice' and 'after advice' are available, but in the most cases, it's enough to solve your problem.
Note that it may be required adding 'dynamic' keyword to your function, when the interception against pure Swift class/method doesn't work correctly.
MOAspects is superior to two most famous AOP library for Objective-C, Aspects and BlockInjection.
Aspects doesn't support class method interception and multiple hooking into methods in class hierarchy.
BlockInjection has a critical issue not to support 64-bit.

Zend Di vs ServiceManager dependency injection containers

What is DI for and what is its use case, when we have ServiceManager?
They appear to be similar since in configuration files for both zend-di and zend-servicemanager we can set up some options such as aliases and invokables.
I am trying to get a better understanding of what is happening behind the scenes with these components, and documentation did not give me enough info.
Could you please tell me what the difference is and when I should use Di instead of ServiceManager?
Zend\DI relies on magic, like reflections, to detect and inject dependencies while service manager uses user provided factories. That is main difference.
Di sort of deprecated in community in favor of SM due to complexity, debugging and performance issues.
It supposed to be good for RAD, but you need above average knowledge to use it properly.
On the other hand SM have pretty verbose and explicit wiring, you can open your code year later and easily figure out what is going on.
Zend\Di takes care of wiring your classes together, whereas with Zend\ServiceManager you have to wire things manually and write a factory closure for every class you want to instantiate.
Zend\ServiceManager is much faster since it does not rely on the slow Reflection API. On the other hand, writing closures for large applications with hundreds of classes becomes very tedious. Keeping your closures up-to-date will get trickier as your application grows.
To address this problem, I have written a Zend Framework 2 module called ZendDiCompiler. It relies on Zend\Di to scan your code and auto-generates factory code to instantiate your classes. You get the best of both components: the power of Zend\Di and the performance of Zend\ServiceManager.
I have put quite a bit of work into the documentation of ZendDiCompiler and some easy and more advanced usage examples are provided, too.
Basically the difference is as follows:
Zend\ZerviceManager = Factory driven IoC Container
Zend\Di = Autowiring IoC implementation
Zend\Di was Refactored for Version 3. Its behaviour now more solid and predictable than v2 and it is designed to integrate seamlessly into zend-servicemanager to provide auto-wiring capabilities (no more odd magic). Since it uses PHP's reflection api to resolve dependencies it is slower than a factory driven approach. Therefore version 3 comes with an AoT compiler to create a pre-resolved Injector that omits the use of Reflection. An additional benefit: The generated factories can also be used with Zend\ServiceManager directly.
There is a guide for using AoT with both components: https://zendframework.github.io/zend-di/cookbook/aot-guide/

Why should I care about RTTI in Delphi?

I've heard a lot about the new/improved RTTI capabilities of Delphi 2010, but I must admit my ignorance...I don't understand it. I know every version of Delphi has supported RTTI...and I know that RTTI (Runtime Type Information) allows me to access type information while my application is running.
But what exactly does that mean? Is Delphi 2010's RTTI support the same thing as reflection in .NET?
Could someone please explain why RTTI is useful? Pretend I'm your pointy haired boss and help me understand why RTTI is cool. How might I use it in a real-world application?
RTTI in Delphi is still not quite as full-featured as Reflection in .NET or other managed languages, because it is operating on compiled code, not an Intermediate Language (bytecode). However, it is a very similar concept, and the new RTTI system in Delphi 2010 brings it a lot closer to reflection, exposing an entire object-oriented API.
Pre-D2010, the RTTI was pretty limited. About the only thing I ever remember doing with it was converting an enumerated type to a string (or vice versa) for use in drop-down lists. I may have used it at one point for control persistence.
With the new RTTI in D2010 you can do a lot more things:
XML Serialization
Attribute-based metadata (TCustomAttribute). Typical use cases would be automatic validation of properties and automated permission checks, two things that you normally have to write a lot of code for.
Adding Active Scripting support (i.e. using the Windows script control)
Building a plug-in system; you could do this before, but there were a lot of headaches. I wasn't able to find a really good example of someone doing this from top to bottom, but all of the necessary functions are available now.
It looks like someone's even trying to implement Spring (DI framework) for Delphi 2010.
So it's definitely very useful, although I'm not sure how well you'd be able to explain it to a PHB; most of its usefulness is probably going to be realized through 3rd-party libraries and frameworks, much the same way it works in the .NET community today - it's rare to see reflection code sitting in the business logic, but a typical app will make use of several reflection-based components like an Object-Relational Mapper or IoC Container.
Have I answered the question?
D2010's extended RTTI is a lot like C#'s reflection. It gives you the ability to get at any field of an object, or inspect its methods. This has all sorts of potential uses. For example, if you can read any field of an object, you can write serialization code that can work with any object. And the ability to inspect methods and obtain their name and signature makes a class much easier to register with a scripting engine.
To me, that's the primary advantage of extended RTTI: The ability to write code that works with any class by examining its members, instead of writing different versions of the same code over and over, tailored to each individual class.
Most people probably won't use it in a real world application.
The people who will use it are the framework builders. Frameworks such as DUnit make extensive use of RTTI.
With the new RTTI capabilities we should expect to start seeing more advanced frameworks and tools appearing, similar to what is available for .NET. These frameworks will revolutionise your development moreso than RTTI will on it's own.
RTTI in Delphi has always been important since version 1.0. Classic RTTI features include the "published" properties section of Classes, which allowed the Object Inspector and the component designtime features to work. For my purposes, I would often use Published class properties to allow for enumeration of those properties at runtime. To store things from my objects to disk, for persistence.
The Delphi 2010 RTTI extends this classic RTTI massively, so much so that you could be forgiven for thinking Delphi did not even have RTTI until delphi 2010.
I would say the #1 most useful applications of "The New RTTI" are (as several other answers already state) going to be in Frameworks written by the gurus, that:
Handle persistence to files or databases. Database and configuration or document saving/loading frameworks and components would use this under the hood.
Handle pickling/marshalling/encoding/decoding to and from various
over-the-wire formats, like JSON, XML, EDI, and other things.
Unit testing was mentioned by someone else (JUnit), but I think perhaps the same frameworks could be really handy for debug and error reporting tools. Given an object passed as a parameter, on the stack, why not have bug reports that can dump all the data that was passed along to a function that failed, and not just a list of functions?
As you can see, some creative people are likely to think of even more uses for this. You could say, that though it does not bring parity to .NET reflection (which another answer speaks more about), it does bring a lot of "dynamic language" features (Think of Perl, Python, JavaScript) to an otherwise strongly typed static-type systems world of Delphi.
For me, personally, extended RTTI gave a possibility to retrieve calling convention from the method pointer. However, currently, that code is under conditional directive, because i am not satisfied with it.
(Critics and suggestions on workarond with basic RTTI are welcome, tho)
Look for TMS Aurelius and you will see that RTTI Attributes are very useful in terms of creating an ORM DataBase Framework and XML Serialization into pure objects and the opposite too.
You are supposed to care because they put it on the box. Clearly they think that some people will care.
Whether you actually have a use for it is entirely dependent on the nature of your projects. Since you didn't have it before and don't understand why having it now is a benefit, this would suggest to me that you don't have a use for it. It's then up to you whether to spend the time researching the subject further in order to discover whether you might be able to find a use for it.
Whether that is the most productive use of your time in relation to your projects, again is something only you can know.

Resources