On the following page it's described that for non-OData formats it is possible to support next-page links and inline count, by wrapping the query results in a PageResult<T> object.
[http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/supporting-odata-query-options#server-paging](http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/supporting-odata-query-options#server-paging)
But it's not mentioned that if you use this type as return type, that the help page does not show any sample data. Instead it shows "Sample not available.".
Currently the GenerateComplexObject method in the ObjectGenerator class tries to instantiate a PageResult<T> object by using the following code:
```
ConstructorInfo defaultCtor = type.GetConstructor(Type.EmptyTypes);
if (defaultCtor == null)
{
// Cannot instantiate the type because it doesn't have a default constructor
return null;
}
result = defaultCtor.Invoke(new object[0]);
```
Which of course fails because PageResult<T> does not have a default constructor.
The solution would be to change the GenerateObject(Type type, Dictionary<Type, object> createdObjectReferences) method in the ObjectGenerator from this:
```
if (type.IsGenericType)
{
return GenerateGenericType(type, DefaultCollectionSize, createdObjectReferences);
}
```
To this:
```
if (type.IsGenericType)
{
if (type.GetGenericTypeDefinition() == typeof(PageResult<>))
{
Type genericsType = type.GetGenericArguments().First();
Type itemsType = typeof(List<>).MakeGenericType(genericsType);
object items = GenerateCollection(itemsType, DefaultCollectionSize, createdObjectReferences);
Type[] constructorTypes = new[]
{
itemsType,
typeof(Uri),
typeof(long?)
};
ConstructorInfo constructor = type.GetConstructor(constructorTypes);
object[] constructorValues = new object[]
{
items, null, (long?)DefaultCollectionSize
};
return constructor.Invoke(constructorValues);
}
else
{
return GenerateGenericType(type, DefaultCollectionSize, createdObjectReferences);
}
}
```
What this modification does is that it checks if the current type you currently are trying to generate sample data for is of type PageResult<>. If not, the same method is called as before. If yes, the following happens:
* The type of the T in PageResult<T> is retrieved
* The type of Items property in PageResult<T> is retrieved
* Using the existing method GenerateCollection a sample collection is constructed
* The constructorTypes variable defines the signature of the PageResult<T> constructor
* The ConstructorInfo object is instantiated based on the constructorTypes
* The constructorValues variable holds the values that are needed when constructing a PageResult<T> object.
* And lastly the constructor.Invoke method will return a new PageResult<T> object with both the Items as well as the Count properties filled in with sample data.
Comments: Provided way to hook in object factories in commits [ece9a1616907](https://aspnetwebstack.codeplex.com/SourceControl/changeset/ece9a16169074ea1fb567506f22fddcf8415352c) for 3.1 and [d618b469626c](https://aspnetwebstack.codeplex.com/SourceControl/changeset/d618b469626cdc9f628d200e9ccbc66a4e141475) for 3.2. Minor comment touch-ups in subsequent commits. Provided approach is more general than attempting to run through all public constructors of a type and somewhat simpler than sub-classing `HelpPageSampleGenerator` just to override `GetSampleObject()`. See `HelpPageConfig` for an example using this to support `PageResult<T>` samples.
[http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/supporting-odata-query-options#server-paging](http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/supporting-odata-query-options#server-paging)
But it's not mentioned that if you use this type as return type, that the help page does not show any sample data. Instead it shows "Sample not available.".
Currently the GenerateComplexObject method in the ObjectGenerator class tries to instantiate a PageResult<T> object by using the following code:
```
ConstructorInfo defaultCtor = type.GetConstructor(Type.EmptyTypes);
if (defaultCtor == null)
{
// Cannot instantiate the type because it doesn't have a default constructor
return null;
}
result = defaultCtor.Invoke(new object[0]);
```
Which of course fails because PageResult<T> does not have a default constructor.
The solution would be to change the GenerateObject(Type type, Dictionary<Type, object> createdObjectReferences) method in the ObjectGenerator from this:
```
if (type.IsGenericType)
{
return GenerateGenericType(type, DefaultCollectionSize, createdObjectReferences);
}
```
To this:
```
if (type.IsGenericType)
{
if (type.GetGenericTypeDefinition() == typeof(PageResult<>))
{
Type genericsType = type.GetGenericArguments().First();
Type itemsType = typeof(List<>).MakeGenericType(genericsType);
object items = GenerateCollection(itemsType, DefaultCollectionSize, createdObjectReferences);
Type[] constructorTypes = new[]
{
itemsType,
typeof(Uri),
typeof(long?)
};
ConstructorInfo constructor = type.GetConstructor(constructorTypes);
object[] constructorValues = new object[]
{
items, null, (long?)DefaultCollectionSize
};
return constructor.Invoke(constructorValues);
}
else
{
return GenerateGenericType(type, DefaultCollectionSize, createdObjectReferences);
}
}
```
What this modification does is that it checks if the current type you currently are trying to generate sample data for is of type PageResult<>. If not, the same method is called as before. If yes, the following happens:
* The type of the T in PageResult<T> is retrieved
* The type of Items property in PageResult<T> is retrieved
* Using the existing method GenerateCollection a sample collection is constructed
* The constructorTypes variable defines the signature of the PageResult<T> constructor
* The ConstructorInfo object is instantiated based on the constructorTypes
* The constructorValues variable holds the values that are needed when constructing a PageResult<T> object.
* And lastly the constructor.Invoke method will return a new PageResult<T> object with both the Items as well as the Count properties filled in with sample data.
Comments: Provided way to hook in object factories in commits [ece9a1616907](https://aspnetwebstack.codeplex.com/SourceControl/changeset/ece9a16169074ea1fb567506f22fddcf8415352c) for 3.1 and [d618b469626c](https://aspnetwebstack.codeplex.com/SourceControl/changeset/d618b469626cdc9f628d200e9ccbc66a4e141475) for 3.2. Minor comment touch-ups in subsequent commits. Provided approach is more general than attempting to run through all public constructors of a type and somewhat simpler than sub-classing `HelpPageSampleGenerator` just to override `GetSampleObject()`. See `HelpPageConfig` for an example using this to support `PageResult<T>` samples.