The ability to develop custom services in Microsoft Dynamics AX is not new, but the way it is done in Microsoft Dynamics AX 2012 is. Developers can now create a WCF service in a way that is similar to how they would develop a WCF service in a language like C#. Using attributes to create data and service contracts, development is simplified because you don't have to worry about the technical details of serialization and deserialization. These things are all handled by WCF, which allows you to quickly create powerful services.
By the end of this chapter, you will have learned how to use attributes to create data and service contracts and how to use them to create custom services. You will also be able to deploy services and consume them using a WCF client application.
The following topics will be covered in this chapter:
In the previous chapter, we discussed the key components of document services. When developing custom services, there are also a few concepts you should be familiar with, starting with attributes.
Attributes are classes that contain data just like normal classes, but the purpose of this data is different. Attributes contain metadata that describes targets. Targets can be of different types such as classes, interfaces, methods, events, and so on.
Attributes can either be intrinsic or custom. Intrinsic attributes are part of Common Language Runtime (CLR) and are contained in the .NET framework. Custom attributes are attributes that you can create yourself.
Because attributes contain metadata, they are useful only when reflection is used. An example of this is the
DataContract
attribute. The service generation process uses reflection on the classes that the service class uses to determine which of these classes are data contracts.
The following code shows the usage of another attribute called SysObsoleteAttribute
. It tells the compiler to generate warnings or errors, suggesting that the class has become obsolete and should therefore not be used anymore:
[SysObsoleteAttribute("You should be using the SysOperation framework now instead RunBase", false)] class RunBase { }
When you create custom services, you will certainly encounter some attributes in X++ that provide metadata to the service generation process. The following table shows you the most commonly used attributes:
Because a service and client don't necessarily use the same types internally, they must agree on the type that they will use to exchange data. This agreement, or contract if you will, is called a data contract, and is used to describe these datatypes. The data contract is then used to serialize and deserialize the type.
Services use data contracts to describe the parameters and return types for their service operations. However, there are some types that can be serialized without using data contracts. The following types serve as implicit data contracts:
str
, int
, int64
, real
, guid
, utcdatetime
, and date
)One noticeable exception is the X++ AnyType
type, which cannot be used in data contracts. On the other hand, any .NET type that can be serialized by WCF can be used as a data contract, which more than makes up for that.
If you need types other than the ones that are described in the preceding table, you can always create your own data contract in X++. A data contract can be created in the AOT by creating a new class and by adding the DataContractAttribute
attribute to the class declaration. You will do this a lot when developing custom services.
Of course, a class without properties cannot hold any data; so, to complete the data contract, you must add data members in the form of methods. You can use the DataMemberAttribute
attribute to specify that a method is a data member. The data members themselves can use data contracts or any of the types described previously as return types and parameters.
When we talked about the WCF, we saw that a service contract describes the functionality that is exposed. In Microsoft Dynamics AX 2012, you can create a service contract by creating a class in the AOT. This class is called a service
class. A service class does not need an attribute to specify that it is a service contract, although it is required that this class have the RunOn
property set to Server
.
However, when you create such a class, all you have is just a regular class that runs on the server when it is executed. What makes a class a true service class is having methods that are service operations. These methods must have the SysEntryPointAttribute
attribute to indicate that they are service operations.
X++ does not support strongly typed collections, so when we want to return or receive a collection of data contracts, we have to use the
AifCollectionTypeAttribute
class. This attribute is used to specify the type of the collection, both for parameters and return types.
It's possible to specify the following five parameters when using the attribute:
Parameter |
Description |
---|---|
Parameter name |
This specifies the parameter that the attribute applies to. This is either the name of the parameter or |
Item type |
This is the base type of the collection or the key value when the collection is a map. |
Extended type name |
When the type is |
Value type |
When the collection type is a map, this is the type of the value in the map. |
Value extended type name |
When the collection type is a map and the type is |
3.140.197.10