In my previous two posts, I created an Auto Design report using a data method as a Data Report.
Here was the output of the report
And this was the Data Method that provided the data.
using System; using System.Collections.Generic; using System.Security.Permissions; using System.Data; using Microsoft.Dynamics.Framework.Reports; public partial class Report1 { [DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod1() { var datatable = new System.Data.DataTable(); datatable.Columns.Add("Name", typeof(string)); datatable.Columns.Add("Age", typeof(int)); datatable.Rows.Add("Akuma", 78); datatable.Rows.Add("Ryu", 28); datatable.Rows.Add("Ken", 29); datatable.Rows.Add("Guile", 35); datatable.Rows.Add("M.Bison", 41); return datatable; } }
using System; using System.Collections.Generic; using System.Security.Permissions; using System.Data; using Microsoft.Dynamics.Framework.Reports; public partial class Report1 { [DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod1() { var datatable = new System.Data.DataTable();
datatable.Columns.Add("Name", typeof(string)); datatable.Columns.Add("Age", typeof(int));
datatable.Rows.Add("Akuma", 78); datatable.Rows.Add("Ryu", 28); datatable.Rows.Add("Ken", 29); datatable.Rows.Add("Guile", 35); datatable.Rows.Add("M.Bison", 41);
return datatable; } }
In red I’ve highlighted the code I want to focus on.
Ultimately, what you see here is a manual construction of a datatable. As I progress in these examples, we will want to make DataTable construction easier on several levels:
- We want to be strongly typed
- We want to minimize the number of helper classes we need
- We want more seamless integration with existing data sources
- We want to type less
In the attached project I’ve provided static method which will be very useful for us: DataTableFromEnumerable(). Without getting into all the explanation of how it works, they key thing is that this method makes it very easy to create DataTables.
We can rewrite the datamethod above like this …
using System; using System.Collections.Generic; using System.Security.Permissions; using System.Data; using Microsoft.Dynamics.Framework.Reports; using System.Linq; public partial class Report1 { [DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages2() { var records = new[] { new { Name="Akuma", Age=78 }, new { Name="Run", Age=28 }, new { Name="Ken", Age=29 }, new { Name="Guile", Age=25 }, new { Name="M.Bison", Age=41 } }; var datatable = Isotope.Data.DataUtil.DataTableFromEnumerable(records); return datatable; } }
using System; using System.Collections.Generic; using System.Security.Permissions; using System.Data; using Microsoft.Dynamics.Framework.Reports; using System.Linq; public partial class Report1 { [DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages2() {
var records = new[] { new { Name="Akuma", Age=78 }, new { Name="Run", Age=28 }, new { Name="Ken", Age=29 }, new { Name="Guile", Age=25 }, new { Name="M.Bison", Age=41 } }; var datatable = Isotope.Data.DataUtil.DataTableFromEnumerable(records);
return datatable;
}
Which produces this result…
As I write code that illustrated the use of data methods, a persistent problem I have is getting enough data to render to show something big enough to be interesting in a report. One valid approach to this is to construct a sample dataset and store it in a database. Another approach is just to generate dynamically generate fake data to show.
Let’s try that dynamic approach now to dynamically add ages to people.
[DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages3() { int max_age = 60; int min_age = 18; var r = new System.Random(); var names = new string[] { "Akuma", "Ryu", "Ken", "Guile", "M.Bison" , "Chun-Li", "Cammy" , "Blanka", "E.Honda", "Gen", "Birdie", "Adon", "Sagat", "Dhalsim", "Zangief", "Balrog", "Vega"}; var records = from name in names select new { Name = name, Age = r.Next(min_age, max_age) }; var datatable = Isotope.Data.DataUtil.DataTableFromEnumerable(records); return datatable; }
[DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages3() { int max_age = 60; int min_age = 18;
var r = new System.Random(); var names = new string[] { "Akuma", "Ryu", "Ken", "Guile", "M.Bison" , "Chun-Li", "Cammy" , "Blanka", "E.Honda", "Gen", "Birdie", "Adon", "Sagat", "Dhalsim", "Zangief", "Balrog", "Vega"};
var records = from name in names select new { Name = name, Age = r.Next(min_age, max_age) };
var datatable = Isotope.Data.DataUtil.DataTableFromEnumerable(records);
And from that point, it’s pretty easy to generate even more data about the people.
[DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages_and_Weights() { int max_age = 60; int min_age = 18; int min_weight = 140; // weight in pounds int max_weight = 240; var r = new System.Random(); var names = new string[] { "Akuma", "Ryu", "Ken", "Guile", "M.Bison" , "Chun-Li", "Cammy" , "Blanka", "E.Honda", "Gen", "Birdie", "Adon", "Sagat", "Dhalsim", "Zangief", "Balrog", "Vega"}; var records = from name in names select new { Name = name, Age = r.Next(min_age, max_age) , Weight = r.Next(min_weight,max_weight) }; var datatable = Isotope.Data.DataUtil.DataTableFromEnumerable(records); return datatable; }
[DataMethod(), AxSessionPermission(SecurityAction.Assert)] public static System.Data.DataTable DataMethod_Ages_and_Weights() { int max_age = 60; int min_age = 18;
int min_weight = 140; // weight in pounds int max_weight = 240;
var records = from name in names select new { Name = name, Age = r.Next(min_age, max_age) , Weight = r.Next(min_weight,max_weight) };