在客户端程序中通过MDX查询SSAS的数据

这两天在讲解SSAS(SQL Server Anaylysis Service)及其编程。其中有一个话题就是,如何将SSAS的查询结果,显示在我们自定义的应用程序里面。

关于SSAS,是微软在商务智能(BI)平台上的一个最重要的组件,称为分析服务器。如果你还不熟悉,可以先参考这里

课堂上有一个小例子,演示了如何编写程序实现简单的查询。整理出来给有兴趣的朋友参考一下

有几个要点

1。客户端与SSAS的通讯,其实传递是XML/A指令。发起这种指令,可以通过标准的Web Request(封装为一个SOAP包即可),也可以通过客户端API。

2。SQL Server 自带了一个客户端API,Microsoft.AnalysisServices.AdomdClient.dll.这个程序集,一般是在C:Program Files (x86)Microsoft.NETADOMD.NET100Microsoft.AnalysisServices.AdomdClient.dll 这个路径下面。(备注,我是使用64位系统,SQL Server的版本是SQL Server 2008 R2)

3。使用Adomd的方式与标准的ADO.NET还是有相似之处的,也需要有Connection以及Command之类的对象,只不过它的查询语法是所谓的MDX(多维表达式),而且它返回的结果不是一个平面的二维结构,可能会有多个轴(最多可以有128个轴),所以解析的时候会更加复杂些。

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Microsoft.AnalysisServices.AdomdClient;

namespace WindowsFormsApplicationSSASClient
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            Load += new EventHandler(Form1_Load);
        }

        void Form1_Load(object sender, EventArgs e)
        {
            using (var conn = new AdomdConnection("Data Source=localhost;Catalog=Adventure Works DW 2008;"))
            {
                using (var cmd = conn.CreateCommand())
                {
                    cmd.CommandText = "SELECT [Customer].[Customer Geography].[Country] ON 0,[Product].[Product Categories].[Category] ON 1 FROM [Adventure Works]";//这里使用的是MDX语法
                    conn.Open();
                    var result = cmd.ExecuteCellSet();//这是返回一个特殊的CellSet对象,因为SSAS的结果集可能是有多维的

                    var tb = ToDataTable(result);//通过一个标准方法将CellSet转换为DataTable
                    dataGridView1.DataSource = tb;
                }

            }
        }


        public DataTable ToDataTable(CellSet cs)
        {
            DataTable dt = new DataTable();
            dt.TableName = "resulttable";
            DataColumn dc = new DataColumn();
            DataRow dr = null;

            //第一列:必有为维度描述(行头)
            dt.Columns.Add(new DataColumn("Description"));

            //生成数据列对象
            string name;

            foreach (Position p in cs.Axes[0].Positions)
            {
                dc = new DataColumn();
                name = "";
                foreach (Member m in p.Members)
                {
                    name = name + m.Caption + " ";
                }

                dc.ColumnName = name;
                dt.Columns.Add(dc);
            }

            //添加行数据
            int pos = 0;

            foreach (Position py in cs.Axes[1].Positions)
            {
                dr = dt.NewRow();

                //维度描述列数据(行头)
                name = "";

                foreach (Member m in py.Members)
                {
                    name = name + m.Caption + "
";
                }
                dr[0] = name;

                //数据列
                for (int x = 1; x <= cs.Axes[0].Positions.Count; x++)
                {
                    dr[x] = cs[pos++].FormattedValue;
                }
                dt.Rows.Add(dr);
            }
            return dt;
        } 


    }
}
原文地址:https://www.cnblogs.com/martin-roger/p/7218059.html