Translate VB-code to Delphi

Hi,

Below part of some VB.Net code is shown. It is used to interface data to an online application via SOAP.
The full code can be downloaded here
First some info: Code from de WDSL:
    function CreateStamTabelRecord(const PartnerKey: string; const Omgevingscode: string; const SessionId: string; const Stamtabel: Stamtabel; var Primarykey: string; var Foutmelding: string): Boolean; stdcall;

Open in new window

  Stamtabel = class(TRemotable)
  private
    Fschema: TXMLData;
  public
    destructor Destroy; override;
  published
    property schema: TXMLData  Index (IS_REF) read Fschema write Fschema;
  end;

Open in new window


Can anybody translate the following VB-code to Delphi?
The content of ds_mutatie is important to be correct. How should this be created within Delphi?
Private Sub btnCreateNewDeb_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnCreateNewDeb.Click
        If String.IsNullOrEmpty(txtSessionId.Text) Then MsgBox("SessionId is leeg.") : Exit Sub

        Select Case combometh.SelectedItem
            Case "SOAP"
                Dim ws1 As New ws1.ws1
                Dim foutmelding As String = ""
                Dim ds_records As New DataSet

                Dim ds_mutatie As New DataSet
                Dim dt_selection As DataTable = ds_mutatie.Tables.Add : dt_selection.TableName = "METADATA"
                dt_selection.Columns.Add("TABLE", GetType(System.String)).DefaultValue = "DEB"
                Dim dr_selection = dt_selection.NewRow : dt_selection.Rows.Add(dr_selection)

                Dim dt_data As DataTable = ds_mutatie.Tables.Add : dt_data.TableName = "DATA"
                dt_data.Columns.Add("ZKSL", GetType(System.String)).DefaultValue = txtZKSLNieuw.Text

                Dim dr_data = dt_data.NewRow : dt_data.Rows.Add(dr_data)

                Dim MessageId() As String = Nothing
                If Not ws1.CreateStamTabelRecord(txtPartnerKey.Text, txtOmgevingsCode.Text, txtSessionId.Text, ds_mutatie, txtNrNieuw.Text, foutmelding) Then
                    MsgBox("debiteur aangemaakt mislukt: " + foutmelding)
                Else
                    MsgBox("debiteur aangemaakt, deb.nr: " + txtNrNieuw.Text)
                    txtDebNr.Text = txtNrNieuw.Text
                End If
        End Select
    End Sub

Open in new window

<NewDataSet>
<METADATA>
<TABLE>DEB</TABLE>
</METADATA>
<DATA>
<ZKSL>naam debiteur</ZKSL>
</DATA>
</NewDataSet>

Open in new window

Stef MerlijnDeveloperAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

ste5anSenior DeveloperCommented:
This is completely the wrong track.

Just import the WSDL and let Delphi generate the code: Using the WSDL Importer.
1
Stef MerlijnDeveloperAuthor Commented:
I did already import the WDSL in Delphi.
The problem is how to fill the data, as in the VB-example.
0
ste5anSenior DeveloperCommented:
Just provide the information necessary to execute that method. But I guess your problem is the DataSet parameter? How is it tranlated in Delphi? You need to make a runnable VB sample to examine with a sniffer how it is translated. The .NET datasets have a ToXML method. So maybe this format is used..
0
Determine the Perfect Price for Your IT Services

Do you wonder if your IT business is truly profitable or if you should raise your prices? Learn how to calculate your overhead burden with our free interactive tool and use it to determine the right price for your IT services. Download your free eBook now!

Stef MerlijnDeveloperAuthor Commented:
Yes, ds_mutatie (dataset) gives me the headache.
Therefor I hoped someone could understand how VB.Net set this up and translate it to Delphi.
As far as I know the content of the DataSet should reflect to XML-code I posted at the bottom. Elements from that also ocur in the VB.Net code.
I just need to know how to convert that code.

I have Visual Studio installed in order to run the provided VB.Net example, but I'm not able to figure it out.
0
ste5anSenior DeveloperCommented:
The problem is that this web service uses a .NET class as method parameter. Which is a bad idea from the web service author. Cause now the web service depends on how .NET serialzes this data type, the data set.

I woul guess the dataset is serialized into the default XML dataset representation also used when using the dataset GetXml() method.

But you need to verify this first. Thus you need a working VB sample client. Then you need to sniff the traffic to see how it is really serialized.
0
Stef MerlijnDeveloperAuthor Commented:
ds_mutatie is of class Stamtabel which is a TXMLData (declaration is also mentioned in my first post).
Till now I came up with something like this:
procedure TForm1.btDebiteurMakenClick(Sender: TObject);
var lError: string;
    IDforNewRecord : String;
    ds_mutatie : Stamtabel;
    xData : TXMLData;
begin
  IDforNewRecord := '18888';
//  ds_mutatie := Stamtabel.Create; // uses Soap.XSBuiltIns
//  ds_mutatie.schema.LoadFromXML(Memo1.Lines.text);  // here is the xml content to send
//  xData := TXMLData.Create;    // uses Soap.XSBuiltIns
//  xData.LoadFromXML(Memo1.Lines.text);  // here is the xml content to send
//  ds_mutatie.Schema := xData.ToString;
  if NOT ws1.CreateStamTabelRecord(cPartnerKey , cOmgevingsCode , fSessionId , ds_mutatie, IDforNewRecord, lError) then
    MessageDlg('Create record error: ' + lError, TMsgDlgType.mtError , [mbOK] , 0)
  else
    ShowMessage('Debtor is created: ' + IDforNewRecord)
end;

Open in new window

CONTENT of Memo1:
<NewDataSet>
<METADATA>
<TABLE>DEB</TABLE>
</METADATA>
<DATA>
<NR>18888</NR>
<ZKSL>test debiteur</ZKSL>
<NAAM>Test debiteur</NAAM>
<STRAAT>De Trompet</STRAAT>
<HNR>2880</HNR>
<HNRTV>A</HNRTV>
<POSTCD>1967 DD</POSTCD>
<PLAATS>Heemskerk</PLAATS
><LAND>NL</LAND>
<TEL>0251-241641</TEL>
<FAX>0251-244405</FAX>
<EMAIL>info@muis.nl</EMAIL>
<HOMEPAGE>http://www.muis.nl</HOMEPAGE>
<BNKIBAN>NL38RABO0123456800</BNKIBAN>
<BETALER>10001</BETALER>
<BETCOND>1</BETCOND>
<BTWPL>B</BTWPL>
<BTWNR>NL123436771B01</BTWNR>
<KVKNR>54543737</KVKNR>
</DATA>
</NewDataSet>

Open in new window

0
Sinisa VukSoftware architectCommented:
This is my example:
procedure TForm1.Button1Click(Sender: TObject);
var
  ws1: ws1_xmlSoap;
  foutmelding, Primarykey, Stamtabel: String;
begin
  if Length(txtSessionId.Text) = 0 then
  begin
    ShowMessage('SessionId is leeg.');
    Exit;
  end;

  foutmelding := '';
  Primarykey := '';

  Stamtabel := '';
  Stamtabel := Stamtabel + '<NewDataSet>' + #13#10;
  Stamtabel := Stamtabel + '<METADATA>' + #13#10;
  Stamtabel := Stamtabel + '<TABLE>'+'DEB'+'</TABLE>' + #13#10;
  Stamtabel := Stamtabel + '</METADATA>' + #13#10;
  Stamtabel := Stamtabel + '<DATA>' + #13#10;
  Stamtabel := Stamtabel + '<ZKSL>naam debiteur</ZKSL>' + #13#10;
  Stamtabel := Stamtabel + '</DATA>' + #13#10;
  Stamtabel := Stamtabel + '</NewDataSet>';

  //create soap call
  ws1 := Getws1_xmlSoap();
  try
    //need to call Login first ...
    if not ws1.CreateStamTabelRecord(txtPartnerKey.Text, txtOmgevingsCode.Text, txtSessionId.Text,
      Stamtabel, Primarykey, foutmelding) then
    begin
      ShowMessage('debiteur aangemaakt mislukt: ' + foutmelding);
    end
    else
    begin
      ShowMessage('debiteur aangemaakt, deb.nr: ' + txtNrNieuw.Text);
      txtDebNr.Text := txtNrNieuw.Text;
    end;
  finally
    ws1 := nil;
  end;
end;

Open in new window


note... I assume that you need to call Login first... and before that obtain PartnerKey and Omgevingscode...
Using soap is a quite easy ...
...and main thing is to build proper xml definition of a table/row/data string.
0
ste5anSenior DeveloperCommented:
A dataset is not strongly typed. You can pass any kind of dataset, thus any XML. Either you ask the web service provider for the correct data set layout or you try and error..
0
Stef MerlijnDeveloperAuthor Commented:
Thus you need a working VB sample client.
Got that already.

Then you need to sniff the traffic to see how it is really serialized.
How would I do that?
0
Sinisa VukSoftware architectCommented:
Using Fiddler you can sniff traffic, and look how soap/xml looks like...
0
ste5anSenior DeveloperCommented:
Either using Fiddler or Wireshark. The first is a HTTP/HTTPS sniffer, the second a generic one.

Using Fiddler to capture SOAP messages

Caveat: both tools should be only installed on development machines. Never on production.
0
Stef MerlijnDeveloperAuthor Commented:
procedure TForm1.btDebiteurMakenClick(Sender: TObject);
var lError: string;
    IDforNewRecord : String;
    v_Stamtabel : String;
    ds_Stamtabel : Stamtabel;
begin
  v_Stamtabel := '';
  v_Stamtabel := v_Stamtabel + '<NewDataSet>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<METADATA>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<TABLE>'+'DEB'+'</TABLE>' + #13#10;
  v_Stamtabel := v_Stamtabel + '</METADATA>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<DATA>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<NR>18888</NR>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<ZKSL>naam debiteur</ZKSL>' + #13#10;
  v_Stamtabel := v_Stamtabel + '<NAAM>naam debiteur</NAAM>' + #13#10;
  v_Stamtabel := v_Stamtabel + '</DATA>' + #13#10;
  v_Stamtabel := v_Stamtabel + '</NewDataSet>';
  ds_Stamtabel := Stamtabel.Create; // uses Soap.XSBuiltIns
  //  AND HERE ???
  //  I need to assign the content of v_Stamtabel (String) to ds_Stamtabel (Stamtabel = TXMLData) ?

Open in new window

0
ste5anSenior DeveloperCommented:
E.g.

Stamtabel := TXMLData.Create;
Stamtabel.LoadFromXML(v_Stamtabel);

Open in new window

0
Stef MerlijnDeveloperAuthor Commented:
Stamtabel doesn't have a LoadFromXML.
[dcc32 Error] Unit1.pas(187): E2003 Undeclared identifier: 'LoadFromXML'
  Stamtabel = class(TRemotable)
  private
    Fschema: TXMLData;
  public
    destructor Destroy; override;
  published
    property schema: TXMLData  Index (IS_REF) read Fschema write Fschema;
  end;

Open in new window

0
ste5anSenior DeveloperCommented:
Try writing it to schema.
0
Stef MerlijnDeveloperAuthor Commented:
If it only was so easy Pfff
  ds_Stamtabel := Stamtabel.Create; // uses Soap.XSBuiltIns
  ds_Stamtabel.schema.LoadFromXML(v_Stamtabel);

Open in new window

Exception at this code in unit Soap.XSBuiltIns
procedure TXMLData.LoadFromXML(const XML: string);
begin
  FXMLDocument.LoadFromXML(XML);
  if FXMLDocument.Node.ChildNodes.Count > 0 then
    FXMLNode := FXMLDocument.Node.ChildNodes[0];
end;

Open in new window

0
ste5anSenior DeveloperCommented:
What exception?
0
Stef MerlijnDeveloperAuthor Commented:
Access Violation Read of Address
0
Stef MerlijnDeveloperAuthor Commented:
0
Stef MerlijnDeveloperAuthor Commented:
I've hired a freelancer and after investigation he reported back to me that the SOAP version of the interface in combination with a MS DataSet only could be done via a dirty hack (see: http://www.gekko-software.nl/DotNet/Art07.htm).
For that reason we've decided to use the XML-verion of the interface which now works fine in Delphi.
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
Stef MerlijnDeveloperAuthor Commented:
None of the other proposed solutions solved my issue.
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Visual Basic.NET

From novice to tech pro — start learning today.