2011-06-10 59 views
1

以找到所有擁有多個開放式電話呼叫的客戶爲例。在SQL中,一個HAVING子句可以讓你獲得大部分的方式。在CRM SDK中,這會變得更加困難,我敢打賭,只有CRM服務器才能處理通過網絡發送的更多數據。從Dynamics CRM SDK獲取數據庫連接字符串

因此,我希望我的插件,應用程序,自定義工作流通過過濾視圖讀取數據庫,然後通過Web服務更改需要的內容。

問題:如何從SDK中獲取組織背後數據庫的數據庫連接字符串?

當然,我知道它現在是什麼,可以硬編碼或配置它。但我希望用戶使用發現服務和應用程序找到他們的CRM實例來處理其餘的事情。

剛剛從一個快速測試,簡單的SQL

SELECT subject, phonenumber, createdon FROM FilteredPhoneCall WHERE activityid = @phoneCallID 

比SDK的檢索方法快4倍左右。

回答

1

我不知道從SDK/WebServices訪問該信息的任何方式,我通常將連接字符串保存在配置文件或項目設置中。

有很多,可以根據安裝設置改變的因素:

  • DB服務器名稱
  • 安裝型(內部部署,IFD等)
  • DB身份驗證(集成,密碼等)

但是,如果您在本地部署中使用集成安全性,您可能會隨時隨地創建連接字符串...

string dbServerName = "SERVERNAME"; 
string orgName = getOrgNameFromDiscoveryService(); 

string connectionString = String.Format("Data Source={0};Initial Catalog={1}__MSCRM;Integrated Security=True", dbServerName, orgName); 

//create sql connection 
+0

服務器名稱是癥結所在。我處理場所安裝,並使用集成身份驗證,因此這些都不是(至少對我而言)。 – 2011-06-17 13:09:01

3

據我所知,沒有辦法從組織服務獲取數據庫服務器名稱。您可以使用部署服務(請參閱http://worldofdynamics.blogspot.com/2011/12/dynamics-crm-2011-c-code-for-retrieving.html)檢索它,但除非您是部署管理員 - 即使是檢索,該服務也沒有用處。

我知道,查看數據庫信息的唯一方法是將視圖/高級查找導出到動態電子表格 - 連接信息嵌入在Excel XML中。

我開發了一個靜態方法,給定Org Url,將下載一個動態電子表格並解析出連接字符串。

/// <summary> 
    /// Given a Dynamics CRM Org URL, retrieve the Database Connection string 
    /// </summary> 
    /// <param name="crmOrgUrlBase"></param> 
    /// <returns></returns> 
    private static string GetCrmDatabaseConnectionString(string crmOrgUrlBase) 
    { 
     string cleanurl = crmOrgUrlBase.ToLowerInvariant().Trim().Replace("/xrmservices/2011/organization.svc", ""); 
     { 
      int mainPos = cleanurl.IndexOf("/main.aspx"); 
      if (mainPos > 0) 
      { 
       cleanurl = cleanurl.Substring(0, mainPos); 
      } 
     } 

     string requestPayload = @"xdpi=96&exportType=list&useSqlQuery=1&fetchXml=%3Cfetch+distinct%3D%22false%22+no-lock%3D%22false%22+mapping%3D%22logical%22+page%3D%221%22+count%3D%2250%22+returntotalrecordcount%3D%22true%22%3E%3Centity+name%3D%22systemuser%22%3E%3Cattribute+name%3D%22systemuserid%22%2F%3E%3Cattribute+name%3D%22fullname%22%2F%3E%3Cattribute+name%3D%22fullname%22%2F%3E%3Corder+attribute%3D%22fullname%22+descending%3D%22false%22%2F%3E%3C%2Fentity%3E%3C%2Ffetch%3E%0D%0A&layoutXml=%3Cgrid+name%3D%22excelGrid%22+select%3D%220%22+icon%3D%220%22+preview%3D%220%22%3E%3Crow+name%3D%22result%22+id%3D%22systemuserid%22%3E%3Ccell+name%3D%22fullname%22+width%3D%22100%22%2F%3E%3C%2Frow%3E%3C%2Fgrid%3E%0D%0A"; 
     string url = cleanurl + "/_grid/print/export_live.aspx"; 

     string response = null; 


     using (var wc = new System.Net.WebClient()) 
     { 
      wc.UseDefaultCredentials = true; 
      wc.Headers.Add("Accept-Encoding", "gzip, deflate"); 
      wc.Headers.Add("Content-Type", "application/x-www-form-urlencoded"); 
      wc.Headers.Add("DNT", "1"); 
      response = wc.UploadString(url, requestPayload); 
     } 


     var xe = System.Xml.Linq.XElement.Parse(response); 


     System.Xml.Linq.XNamespace nn = "urn:schemas-microsoft-com:office:spreadsheet"; 
     System.Xml.Linq.XNamespace nn2 = "urn:schemas-microsoft-com:office:excel"; 


     var connectionEl = xe.Element(nn + "Worksheet").Element(nn2 + "QueryTable").Element(nn2 + "QuerySource").Element(nn2 + "Connection"); 

     string rawString = connectionEl.Value; 

     Regex rex = new Regex("SERVER=([^;]+);DATABASE=([^;]+)", RegexOptions.Compiled); 

     var m = rex.Match(rawString); 

     string server = m.Groups[1].Value; 
     string database = m.Groups[2].Value; 

     return "DATA SOURCE=" + server +";INITIAL CATALOG=" + database + ";Integrated Security=SSPI"; 
    } 

它使用針對用戶一個簡單的查詢 - 查詢其實並不重要,因爲我們需要的是數據庫連接字符串。

我原來的博客文章是在這裏: http://www.shulerent.com/2015/01/19/get-the-sql-server-and-database-name-from-dynamics-crm/

+0

感謝您分享此代碼段。它爲我工作。最初,我遇到了(401)未經授權的錯誤。然後,我在WebClient上添加了憑證,並且完美運行。再次感謝。 – 2017-01-30 23:47:50