C# 用nco Call SapRfc函式
阿新 • • 發佈:2020-08-06
首先呼叫sap有兩種方式,一種是用VB或者VB.net ,新建VB類庫 並新增類
Functions類
Public Class Functions Implements IFunctions Private m_sapObject As Object 'sap遠端函式呼叫物件 Protected m_sapFun As Object 'sap函式 Private m_sapConnection As Object '與SAP的連線 ''' <summary> ''' 建構函式,傳入sap的基本資訊''' </summary> ''' <param name="sapSystem">Sap系統,可以傳入null</param> ''' <param name="applicationServer">SAP伺服器ip</param> ''' <param name="Client">集團號,如800</param> ''' <param name="SystemNumber">系統編號,如00</param> ''' <remarks></remarks>Public Sub New(ByVal sapSystem As String, ByVal ApplicationServer As String, ByVal Client As String, ByVal SystemNumber As String) Me.m_sapObject = CreateObject("SAP.Functions") Me.m_sapConnection = Me.m_sapObject.Connection() If String.IsNullOrEmpty(sapSystem) = False ThenMe.m_sapConnection.System = sapSystem End If Me.m_sapConnection.ApplicationServer = ApplicationServer Me.m_sapConnection.Client = Client Me.m_sapConnection.SystemNumber = SystemNumber End Sub ''' <summary> ''' 登入SAP,成功,返回True,失敗,返回False ''' </summary> ''' <param name="User">使用者</param> ''' <param name="PassWord">口令</param> ''' <param name="Language">語言,如ZH、EN等,可以傳入null</param> ''' <returns>是否登入成功</returns> ''' <remarks></remarks> Public Function ConnectToSAP(User As String, Password As String, Language As String) As Boolean Implements IFunctions.ConnectToSAP Me.m_sapConnection.user = User Me.m_sapConnection.Password = Password If String.IsNullOrEmpty(Language) = False Then Me.m_sapConnection.Language = Language Else Me.m_sapConnection.Language = "EN" End If Me.m_sapObject.AutoLogon = True '自動登入 Return Me.m_sapObject.Connection.logon(0, True) '登入是否成功 End Function ''' <summary> ''' 設定呼叫的sap函式名稱 ''' </summary> ''' <param name="sapFuncName">sap函式名稱</param> ''' <remarks></remarks> Public Sub SetFuncName(sapFuncName As String) Implements IFunctions.SetFuncName Me.m_sapFun = Me.m_sapObject.Add(sapFuncName) If m_sapFun Is Nothing Then Throw New Exception("Sap遠端函式名無效:" + sapFuncName) End If End Sub ''' <summary> ''' 設定Sap函式的傳入呼叫引數 ''' </summary> ''' <param name="paramName">引數名稱</param> ''' <param name="paramValue">引數值</param> ''' <remarks></remarks> Public Sub SetParamName(paramName As String, paramValue As Object) Implements IFunctions.SetParamName Dim param As Object param = Me.m_sapFun.Exports(paramName) If param Is Nothing Then Throw New Exception("Sap遠端函式的引數名無效:" + paramName) End If param.Value = paramValue End Sub ''' <summary> ''' 設定sap的傳入內表,用dt_value模擬這個內表 ''' </summary> ''' <param name="SapTableName">sap函式傳入內表的名字</param> ''' <param name="dt_value">模擬的DataTable,要求與傳入內表的欄位名一致</param> ''' <remarks></remarks> Public Sub SetInPutTable(SapTableName As String, dt_value As DataTable) Implements IFunctions.SetInPutTable Dim sapdata As Object 'sap傳入內表 Dim saprow As Object 'sap傳入內表的一行 Dim dc As DataColumn Dim index As Integer sapdata = Me.m_sapFun.Tables(SapTableName) For index = 0 To dt_value.Rows.Count - 1 '迴圈表,並給sap傳入內表賦值 saprow = sapdata.Rows.Add() '傳入內表新增一行記錄,下面為傳入內表記錄賦值 For Each dc In dt_value.Columns saprow(dc.ColumnName) = dt_value.Rows(index)(dc.ColumnName).ToString() Next Next End Sub ''' <summary> ''' 當引數設定完成後,執行函式呼叫 ''' </summary> ''' <remarks></remarks> Public Sub ExecFun() Implements IFunctions.ExecFun If Me.m_sapFun.Call() = False Then Throw New Exception("Sap遠端函式呼叫失敗。") '從SAP取數出錯,退出函式 End If End Sub ''' <summary> ''' 根據欄位列表(逗號分隔)建立指定欄位的DataTable ''' </summary> ''' <param name="fields">欄位列表(逗號分隔)</param> ''' <returns>空表</returns> ''' <remarks></remarks> Public Function CreateTable(fields As String) As DataTable Implements IFunctions.CreateTable Dim dt As New DataTable Dim strs As String() Dim s As String strs = fields.Split(",") For Each s In strs dt.Columns.Add(s.Trim()) Next Return dt End Function ''' <summary> ''' 取得sap的傳出引數值 ''' </summary> ''' <param name="paramName">傳出引數名</param> ''' <returns>傳出引數值</returns> ''' <remarks></remarks> Public Function GetOutPutParam(paramName As String) As String Implements IFunctions.GetOutPutParam Dim param As Object param = Me.m_sapFun.Imports(paramName) If param Is Nothing Then Throw New Exception("Sap遠端函式的引數名無效:" + paramName) End If If param.Value Is Nothing Then Return "" Else Return param.Value.ToString() End If End Function ''' <summary> ''' 把sap函式呼叫結構的傳出內錶轉成dotNet的表 ''' </summary> ''' <param name="fields">sap傳出內表的欄位列表,欄位間以逗號分隔</param> ''' <param name="SapTableName">sap傳出內表的表名</param> ''' <param name="strTrim">是否清除前後空格</param> ''' <returns>把sap內表匯出的dotnet表,欄位都為string型</returns> ''' <remarks></remarks> Public Function GetOutPutTable(fields As String, SapTableName As String, strTrim As Boolean) As DataTable Implements IFunctions.GetOutPutTable '按欄位列表建立表,fields中的欄位列表用逗號分隔 Dim dt As DataTable dt = Me.CreateTable(fields) '從sap表中讀資料,迴圈sap中取得的資料,寫入dt Dim sapdata As Object Dim saprow As Object Dim dr As DataRow '資料增加的新行 Dim dc As DataColumn sapdata = Me.m_sapFun.Tables(SapTableName) For Each saprow In sapdata.Rows dr = dt.NewRow() For Each dc In dt.Columns If strTrim = True Then dr(dc.ColumnName) = saprow(dc.ColumnName).ToString().Trim() Else dr(dc.ColumnName) = saprow(dc.ColumnName).ToString() End If Next dt.Rows.Add(dr) Next Return dt End Function ''' <summary> ''' 關閉sap的連線 ''' </summary> ''' <remarks></remarks> Public Sub DisConnectSAP() Implements IFunctions.DisConnectSAP Me.m_sapConnection.logoff() End Sub End Class
C#引入類庫,並呼叫:
SapHelper sap = new SapHelper("127.0.0.1", "SFC_USER", "yhpwd", "801", "04", "EN"); SoDetailConn.SetFuncName("ZRFC_GET_SALES_DETAIL");//執行的RFC名稱 SoDetailConn.SetParamName("ORDERNUM", ""); SoDetailConn.SetParamName("PLANT", ""); SoDetailConn.ExecFun();//執行這個RFC DataTable outPutTable = SoDetailConn.GetOutPutTable("aa,bb", "table1", true);//返回的Table
專案右鍵引入rscp4n 、sapnco 、sapnco.utils三個引用
saphelper如下
public class SapHelper { private RfcConfigParameters parms = null; private RfcDestination prd = null; /// <summary> /// Sap初始化 /// </summary> /// <param name="Server">ip地址</param> /// <param name="UseID">登入sap賬號</param> /// <param name="Password">密碼</param> /// <param name="Client">埠號</param> /// <param name="SysNumber">系統編號,如00</param> /// <param name="Language">語言,如ZH、EN等,可以傳入null</param> public SapHelper(string Server, string UseID, string Password, string Client, string SysNumber, string Language) { parms = new RfcConfigParameters(); //parms.Add(RfcConfigParameters.Name, "mycon"); //parms.Add(RfcConfigParameters.AppServerHost, "10.134.28.112"); //parms.Add(RfcConfigParameters.SystemNumber, "00"); //parms.Add(RfcConfigParameters.User, "accadm"); //parms.Add(RfcConfigParameters.Password, "1707sap"); //parms.Add(RfcConfigParameters.Client, "801"); //parms.Add(RfcConfigParameters.Language, "EN"); parms.Add(RfcConfigParameters.Name, "mycon"); parms.Add(RfcConfigParameters.AppServerHost, Server); parms.Add(RfcConfigParameters.User, UseID); parms.Add(RfcConfigParameters.Password, Password); parms.Add(RfcConfigParameters.Client, Client); parms.Add(RfcConfigParameters.SystemNumber, SysNumber); parms.Add(RfcConfigParameters.Language, Language); parms.Add(RfcConfigParameters.PoolSize, "5"); parms.Add(RfcConfigParameters.PeakConnectionsLimit, "10"); parms.Add(RfcConfigParameters.IdleTimeout, "10"); prd = RfcDestinationManager.GetDestination(parms); } public List<Sapinfo> CallRfc(string functionname, String plant, String ref1, String ref2) { List<Sapinfo> list = new List<Sapinfo>(); //獲取Repository物件 RfcRepository repo = prd.Repository; if (functionname.Equals("ZRFC_GET_SALES_DETAIL")) { //指定函式 IRfcFunction mySapFunction = repo.CreateFunction(functionname); //設定引數 mySapFunction.SetValue(3, ref2); mySapFunction.SetValue(4, plant); //IRfcTable tables = mySapFunction.GetTable("TIMETICKETS"); //IRfcStructure struSAP = tables.Metadata.LineType.CreateStructure(); //struSAP.SetValue("ORDERID", workorderId); //struSAP.SetValue("OPERATION", "0010"); //struSAP.SetValue("POSTG_DATE", ""); //struSAP.SetValue("Yield", Num); //tables.Append(struSAP); //函式執行 mySapFunction.Invoke(prd); //獲取結果 IRfcTable outReturnTable = mySapFunction.GetTable("SOSKU"); //遍歷放回結果 outReturnTable.AsEnumerable().ToList().ForEach(x => { list.Add(new Sapinfo() { orderno = x.GetString("VBELN"), skuno = x.GetString("MATNR"), price = x.GetDouble("NETPR") + "", packageno = x.GetInt("POSNR") + "", shiporderno1 = null, shiporderno2 = null, Pgidate = null }); }); //for (int i = 0; i < outReturnTable.RowCount; i++) //{ // outReturnTable.CurrentIndex = i; // String so = outReturnTable.CurrentRow.GetString("VBELN"); // so // String pn = outReturnTable.CurrentRow.GetString("MATNR"); // pn // double price = outReturnTable.CurrentRow.GetDouble("NETPR");// 單價 // int packageno = outReturnTable.CurrentRow.GetInt("POSNR"); // list.Add(new Sapinfo(so, pn, price + "", packageno + "", null, null, null)); //} } else if (functionname.Equals("ZRFC_CES_SHIP_DETAIL")) { IRfcFunction mySapFunction = repo.CreateFunction(functionname); //設定引數 mySapFunction.SetValue(0, ref2); mySapFunction.SetValue(1, plant); //IRfcTable tables = mySapFunction.GetTable("TIMETICKETS"); //IRfcStructure struSAP = tables.Metadata.LineType.CreateStructure(); //struSAP.SetValue("ORDERID", workorderId); //struSAP.SetValue("OPERATION", "0010"); //struSAP.SetValue("POSTG_DATE", ""); //struSAP.SetValue("Yield", Num); //tables.Append(struSAP); //函式執行 mySapFunction.Invoke(prd); //獲取結果 IRfcTable outReturnTable = mySapFunction.GetTable("SHIP01"); //遍歷放回結果 outReturnTable.AsEnumerable().ToList().ForEach(x => { Console.WriteLine(x.GetObject("PGIDATE")); if (x.GetObject("PGIDATE") == null) Console.WriteLine("no PGI"); else list.Add(new Sapinfo() { orderno = null, skuno = null, price = null, packageno = null, shiporderno1 = ref1, shiporderno2 = ref2, Pgidate = x.GetObject("PGIDATE").ToString() + x.GetObject("PGITIME") }); }); //outReturnTable.AsEnumerable().ToList().Where(y=>{!string.IsNullOrEmpty()}).ForEach(x => //{ // if (string.IsNullOrEmpty(x.GetObject("PGIDATE").ToString())) // Console.WriteLine("no PGI"); // else // list.Add(new Sapinfo() // { // orderno = null, // skuno = null, // price = null, // packageno = null, // shiporderno1 = ref1, // shiporderno2 = ref2, // Pgidate = x.GetObject("PGIDATE").ToString() + x.GetObject("PGITIME") // }); //}); } else if (functionname.Equals("ZRFC_SEND_ST_SHIPMENT")) { } return list; } public List<B2Bdata> callRfcshipment(string functionname, String plant, String ref1, String ref2) { List<B2Bdata> list = new List<B2Bdata>(); RfcRepository repo = prd.Repository; if (functionname.Equals("ZRFC_SEND_ST_SHIPMENT")) { IRfcFunction mySapFunction = repo.CreateFunction(functionname); //設定引數 mySapFunction.SetValue(0, ref2); mySapFunction.SetValue(1, plant); //IRfcTable tables = mySapFunction.GetTable("TIMETICKETS"); //IRfcStructure struSAP = tables.Metadata.LineType.CreateStructure(); //struSAP.SetValue("ORDERID", workorderId); //struSAP.SetValue("OPERATION", "0010"); //struSAP.SetValue("POSTG_DATE", ""); //struSAP.SetValue("Yield", Num); //tables.Append(struSAP); //函式執行 mySapFunction.Invoke(prd); //獲取結果 IRfcTable table = mySapFunction.GetTable("HEADER_OUT"); IRfcTable table2 = mySapFunction.GetTable("DETAIL_OUT"); //遍歷放回結果 table2.AsEnumerable().ToList().ForEach(x => { list.Add(new B2Bdata() { PARTNUMBER = x.GetString("KDMAT"), PARTDESCRIPTION = x.GetString("ARKTX"), DROPSHIPPO = x.GetString("PONO"), POLINE = x.GetString("PO_LINE").Replace("^(0+)", ""), SHIPTOCUSTOMERNAME = table.GetString("NAME1"), SHIPTOADDRESS1 = table.GetString("NAME2") + table.GetString("NAME3") + table.GetString("NAME4"), SHIPTOADDRESS2 = table.GetString("NAME_CO") + table.GetString("ADDR2"), SHIPTOADDRESS3 = table.GetString("ADDR3") + table.GetString("ADDR4"), SHIPTOADDRESS4 = table.GetString("ADDR5") + table.GetString("STREET"), SHIPTOCITY = table.GetString("CITY"), SHIPTOSTATE = table.GetString("REGION"), SHIPTOPOSTALCODE = table.GetString("POST_CODE"), SHIPTOCOUNTRY = table.GetString("COUNTRY"), UNITPRICE = string.Empty, SERVICELEVEL = string.Empty, MODEOFTRANSPORT = string.Empty, COSTCENTER = string.Empty, item_no = x.GetString("POSNR").Replace("^(0+)", ""), dn2=x.GetString("DN2") }); }); } return list; } }