Delphi-iocp learning notes ======= server-side data transmission and jsonstreamobject Encoder

Source: Internet
Author: User

Currently, the iocp function still has the server data returned.

Or use netty. The call to the data returned by netty is contenxt. Write (<tobject> OBJ). In this way, the OBJ object is sent to the client.

 

1. encode the returned object into a buffer.

2. Transfer through socket.

 

>>>>>>>>>>>>>

Below I post the process of returning data.

procedure TClientContext.writeObject(const pvDataObject:TObject);var  lvOutBuffer:TBufferLink;begin  lvOutBuffer := TBufferLink.Create;  try    TContextFactory.instance.FEncoder.Encode(pvDataObject, lvOutBuffer);    TIOCPTools.SendBuffer(self.FSocket, lvOutBuffer);  finally    lvOutBuffer.Free;  end;end;

 

During data processing, I tried to call this code.

Procedure tclientcontext. datareceived (const pvdataobject: tobject); var lvjsonstream: tjsonstreamobject; lvfile: string; begin lvjsonstream: = tjsonstreamobject (pvdataobject); // the client sends the file if lvjsonstream. JSON. I ['cmdindex '] = 102 then begin lvfile: = extractfilepath (paramstr (0) + 'tempfile \'; forcedirectories (lvfile); lvfile: = lvfile + lvjsonstream. JSON. s ['file']; tmemorystream (lvjsonstream. stream ). position: = 0; tmemorystream (lvjsonstream. stream ). savetofile (lvfile); End else begin // return data writeobject (lvjsonstream); end; tlogclientwrapper. loginfo (lvjsonstream. JSON. asjson (true); end;

 

In the iocp work thread, if the data is sent completely, the memory block is recycled.

End else if periodata. io_type = io_type_send then begin // send complete data <wsasend> complete // reclaim data block tiodatamempool. instance. givebackiodata (periodata); end;

 

Tiocptools. sendbuffer code

Unit iocptools; interfaceuses ubuffer, jwawinsock2, umempool, windows; const io_type_accept = 1; io_type_recv = 2; io_type_send = 3; // send data type tiocptools = Class (tobject) public class procedure sendbuffer (pvsocket: tsocket; const oubuf: tbufferlink); end; implementationclass procedure tiocptools. sendbuffer (pvsocket: tsocket; const oubuf: tbufferlink); var lvidata: lpper_io_operation_data; lvret: Cardinal ; Begin while oubuf. validcount> 0 do begin lviodata: = tiodatamempool. instance. borrowiodata; lvidata. io_type: = io_type_send; // here I changed the size of the memory block, and the length of each sending cannot exceed the SET SIZE OF THE memory block. If the data is insufficient
// Databuf. Len specifies the size of the memory block to be sent. The memory block size needs to be restored when it is recycled. Lviodata. databuf. len: = oubuf. readbuffer (lviodata. databuf. buf, lviodata. databuf. len); If (wsasend (pvsocket, @ lvidata. databuf, 1, lviodata. workbytes, lvidata. workflag, @ lvidata ^, nil) = socket_error) then begin lvret: = getlasterror (); // overlapped Io. It is normal to see error_io_pending, // indicates that the data has not been received, if data is received, getqueuedcompletionstatus returns the value if (lvret <> error_io_pending) then begin closesocket (pvsocket); break; end.

 

 

// Encoder code, responsible for converting the sent object into a stream

Unit ujsonstreamencoder; interfaceuses uiocpdecoder, ubuffer, classes, superobject, sysutils; Type tjsonstreamencoder = Class (tiocpencoder) public /// <summary> /// encode the object to be sent /// </Summary> /// <Param name = "pvdataobject"> encode the object </ param> // <Param name = "oubuf"> encoded data </param> procedure encode (pvdataobject: tobject; const oubuf: tbufferlink); override; end; implementationuses ujsonstreamobject, windows; Procedure tjsonstreamencoder. encode (pvdataobject: tobject; const oubuf: tbufferlink); var lvjsonstreamobject: tjsonstreamobject; lvjsonlength: integer; lvstreamlength: integer; sdata: string; lvstream: tstream; lvtempbuf: pansichar; begin if pvdataobject = nil then exit; lvjsonstreamobject: = tjsonstreamobject (pvdataobject); sdata: = lvjsonstreamobject. JSON. asjson (true); lvjsonlength: = length (sdata); lvstream: = lvjsonstreamobject. stream; oubuf. addbuffer (@ lvjsonlength, sizeof (lvjsonlength); If lvstream <> nil then begin lvstreamlength: = lvstream. size; end else begin lvstreamlength: = 0; end; oubuf. addbuffer (@ lvstreamlength, sizeof (lvstreamlength); // JSON bytes oubuf. addbuffer (@ sdata [1], lvjsonlength); If lvstreamlength> 0 then begin // stream bytes getmem (lvtempbuf, lvstreamlength); try lvstream. position: = 0; lvstream. readbuffer (lvtempbuf ^, lvstreamlength); oubuf. addbuffer (lvtempbuf, lvstreamlength); finally freemem (lvtempbuf, lvstreamlength); end.

 

>>>>> I have posted all the key code. Demo is not provided this time. Leave a message if necessary

The next learning topic is a demo of stress testing.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.