Skip to content

Commit e2e8025

Browse files
committed
Update uRESTDWMessageCoderMIME.pas
- Correção form-data
1 parent b7b7f11 commit e2e8025

1 file changed

Lines changed: 139 additions & 154 deletions

File tree

CORE/Source/Basic/Mechanics/uRESTDWMessageCoderMIME.pas

Lines changed: 139 additions & 154 deletions
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,6 @@ TRESTDWMessageDecoderMIME = class(TRESTDWMessageDecoder)
8181
TRESTDWMessageEncoderInfoMIME = Class(TRESTDWMessageEncoderInfo)
8282
Public
8383
Constructor Create; Override;
84-
Destructor Destroy; Override;
8584
Procedure InitializeHeaders(AMsg : TRESTDWMessage); Override;
8685
End;
8786

@@ -284,158 +283,149 @@ destructor TRESTDWMessageDecoderMIME.Destroy;
284283

285284
Function TRESTDWMessageDecoderMIME.ReadBody(ADestStream : TStream;
286285
Var VMsgEnd : Boolean) : TRESTDWMessageDecoder;
287-
var
288-
LContentType, LContentTransferEncoding: string;
289-
LDecoder: TRESTDWDecoder;
290-
LBytes : TRESTDWBytes;
291-
LLine: string;
292-
LBuffer: string; //Needed for binhex4 because cannot decode line-by-line.
293-
LIsThisTheFirstLine: Boolean; //Needed for binary encoding
294-
BoundaryStart, BoundaryEnd: string;
295-
IsBinaryContentTransferEncoding: Boolean;
296-
begin
297-
LIsThisTheFirstLine := True;
298-
VMsgEnd := False;
299-
Result := nil;
300-
if FBodyEncoded then begin
301-
LContentType := TRESTDWMessage(Owner).ContentType;
302-
LContentTransferEncoding := TRESTDWMessage(Owner).ContentTransferEncoding;
303-
end else begin
304-
LContentType := FHeaders.Values['Content-Type']; {Do not Localize}
305-
LContentTransferEncoding := FHeaders.Values['Content-Transfer-Encoding']; {Do not Localize}
306-
end;
307-
if LContentTransferEncoding = '' then begin
308-
if IsHeaderMediaType(LContentType, 'application/mac-binhex40') then begin {Do not Localize}
309-
LContentTransferEncoding := 'binhex40'; {do not localize}
310-
end;
311-
end;
312-
313-
// RLebeau 08/17/09 - According to RFC 2045 Section 6.4:
314-
// "If an entity is of type "multipart" the Content-Transfer-Encoding is not
315-
// permitted to have any value other than "7bit", "8bit" or "binary"."
316-
//
317-
// However, came across one message where the "Content-Type" was set to
318-
// "multipart/related" and the "Content-Transfer-Encoding" was set to
319-
// "quoted-printable". Outlook and Thunderbird were apparently able to parse
320-
// the message correctly, but Indy was not. So let's check for that scenario
321-
// and ignore illegal "Content-Transfer-Encoding" values if present...
322-
323-
if IsHeaderMediaType(LContentType, 'multipart') and (LContentTransferEncoding <> '') then {do not localize}
324-
begin
325-
if PosInStrArray(LContentTransferEncoding, ['7bit', '8bit', 'binary'], False) = -1 then begin {do not localize}
326-
LContentTransferEncoding := '';
327-
end;
328-
end;
329-
330-
if TextIsSame(LContentTransferEncoding, 'base64') then begin {Do not Localize}
331-
LDecoder := TRESTDWDecoderMIMELineByLine.Create(nil);
332-
end else if TextIsSame(LContentTransferEncoding, 'quoted-printable') then begin {Do not Localize}
333-
LDecoder := TRESTDWDecoderQuotedPrintable.Create(nil);
334-
end else if TextIsSame(LContentTransferEncoding, 'binhex40') then begin {Do not Localize}
335-
LDecoder := TRESTDWDecoderBinHex4.Create(nil);
336-
end else begin
337-
LDecoder := nil;
338-
end;
339-
Try
340-
if LDecoder <> nil then begin
341-
LDecoder.DecodeBegin(ADestStream);
342-
end;
343-
344-
if MIMEBoundary <> '' then begin
345-
BoundaryStart := '--' + MIMEBoundary; {Do not Localize}
346-
BoundaryEnd := BoundaryStart + '--'; {Do not Localize}
347-
end;
348-
349-
case PosInStrArray(LContentTransferEncoding, ['7bit', 'quoted-printable', 'base64', '8bit', 'binary'], False) of {do not localize}
350-
0..2: IsBinaryContentTransferEncoding := False;
351-
3..4: IsBinaryContentTransferEncoding := True;
352-
else
353-
// According to RFC 2045 Section 6.4:
354-
// "Any entity with an unrecognized Content-Transfer-Encoding must be
355-
// treated as if it has a Content-Type of "application/octet-stream",
356-
// regardless of what the Content-Type header field actually says."
357-
IsBinaryContentTransferEncoding := True;
358-
end;
359-
Repeat
360-
if not FProcessFirstLine then begin
361-
if IsBinaryContentTransferEncoding then
362-
LBytes := ReadLnRFCB(VMsgEnd, EOL, '.') {do not localize}
363-
Else
364-
LLine := ReadLnRFC(VMsgEnd);
365-
end else begin
366-
LLine := FFirstLine;
367-
FFirstLine := ''; {Do not Localize}
368-
FProcessFirstLine := False;
369-
// Do not use ADELIM since always ends with . (standard)
370-
if LLine = '.' then begin {Do not Localize}
371-
VMsgEnd := True;
372-
Break;
373-
end;
374-
if TextStartsWith(LLine, '..') then begin
375-
Delete(LLine, 1, 1);
376-
end;
377-
end;
378-
If (IsBinaryContentTransferEncoding) Then
379-
Begin
380-
If Length(LBytes) > 0 Then
381-
ADestStream.WriteBuffer(LBytes[0], Length(LBytes));
382-
SetLength(LBytes, 0);
383-
If (VMsgEnd) Then
384-
Break;
385-
End;
386-
// New boundary - end self and create new coder
387-
if MIMEBoundary <> '' then begin
388-
if TextIsSame(LLine, BoundaryStart) then begin
389-
Result := TRESTDWMessageDecoderMIME.Create(Owner);
390-
Break;
391-
// End of all coders (not quite ALL coders)
392-
end;
393-
if TextIsSame(LLine, BoundaryEnd) then begin
394-
// POP the boundary
395-
if Owner is TRESTDWMessage then begin
396-
TRESTDWMessage(Owner).MIMEBoundary.Pop;
397-
end;
398-
Break;
399-
end;
400-
end;
401-
if Not Assigned(LDecoder) then
402-
Begin
403-
// Data to save, but not decode
404-
If Not IsBinaryContentTransferEncoding then
405-
If Assigned(ADestStream) then
406-
WriteStringToStream(ADestStream, LLine + EOL);
407-
end
408-
else
409-
begin
410-
// Data to decode
411-
// For TIdDecoderQuotedPrintable, we have to make sure all EOLs are
412-
// intact
413-
if LDecoder is TRESTDWDecoderQuotedPrintable then begin
414-
// For TIdDecoderQuotedPrintable, we have to make sure all EOLs are intact
415-
// LLine := LLine + EOF;
416-
LDecoder.Decode(LLine);
417-
end else if LDecoder is TRESTDWDecoderBinHex4 then begin
418-
//We cannot decode line-by-line because lines don't have a whole
419-
//number of 4-byte blocks due to the : inserted at the start of
420-
//the first line, so buffer the file...
421-
LBuffer := LBuffer + LLine;
422-
end else if LLine <> '' then begin
423-
LDecoder.Decode(LLine);
424-
end;
425-
end;
426-
Until False;
427-
If LDecoder <> Nil Then
286+
Var
287+
LContentType,
288+
LContentTransferEncoding,
289+
LLine,
290+
LBinaryLineBreak,
291+
LBuffer, //Needed for binhex4 because cannot decode line-by-line.
292+
LBoundaryStart,
293+
LBoundaryEnd : String;
294+
LIsThisTheFirstLine, //Needed for binary encoding
295+
LIsBinaryContentTransferEncoding : Boolean;
296+
LDecoder : TRESTDWDecoder;
297+
Begin
298+
LIsThisTheFirstLine := True;
299+
VMsgEnd := False;
300+
Result := Nil;
301+
If FBodyEncoded Then
302+
Begin
303+
LContentType := TRESTDWMessage(Owner).ContentType;
304+
LContentTransferEncoding := TRESTDWMessage(Owner).ContentTransferEncoding;
305+
End
306+
Else
307+
Begin
308+
LContentType := FHeaders.Values['Content-Type']; {Do not Localize}
309+
LContentTransferEncoding := FHeaders.Values['Content-Transfer-Encoding']; {Do not Localize}
310+
End;
311+
If LContentTransferEncoding = '' Then
312+
Begin
313+
If IsHeaderMediaType(LContentType, 'application/mac-binhex40') Then {Do not Localize}
314+
LContentTransferEncoding := 'binhex40' {do not localize}
315+
End
316+
Else If IsHeaderMediaType(LContentType, 'multipart') Then {do not localize}
317+
Begin
318+
If PosInStrArray(LContentTransferEncoding, ['7bit', '8bit', 'binary'], False) = -1 Then {do not localize}
319+
LContentTransferEncoding := '';
320+
End;
321+
If TextIsSame(LContentTransferEncoding, 'base64') Then {Do not Localize}
322+
LDecoder := TRESTDWDecoderMIMELineByLine.Create(Nil)
323+
Else If TextIsSame(LContentTransferEncoding, 'quoted-printable') Then {Do not Localize}
324+
LDecoder := TRESTDWDecoderQuotedPrintable.Create(Nil)
325+
Else If TextIsSame(LContentTransferEncoding, 'binhex40') Then {Do not Localize}
326+
LDecoder := TRESTDWDecoderBinHex4.Create (Nil)
327+
Else
328+
LDecoder := nil;
329+
Try
330+
If LDecoder <> Nil Then
331+
LDecoder.DecodeBegin(ADestStream);
332+
If MIMEBoundary <> '' Then
333+
Begin
334+
LBoundaryStart := '--' + MIMEBoundary; {Do not Localize}
335+
LBoundaryEnd := LBoundaryStart + '--'; {Do not Localize}
336+
End;
337+
If LContentTransferEncoding <> '' Then
338+
Begin
339+
Case PosInStrArray(LContentTransferEncoding, ['7bit', 'quoted-printable', 'base64', '8bit', 'binary'], False) Of {do not localize}
340+
0..2: LIsBinaryContentTransferEncoding := False;
341+
3..4: LIsBinaryContentTransferEncoding := True;
342+
Else
343+
LIsBinaryContentTransferEncoding := True;
344+
LContentTransferEncoding := '';
345+
End;
346+
End
347+
Else
348+
LIsBinaryContentTransferEncoding := True;
349+
Repeat
350+
If Not FProcessFirstLine Then
351+
Begin
352+
If LIsBinaryContentTransferEncoding Then
353+
Begin
354+
LLine := ReadLnRFC(VMsgEnd, EOL, '.'); {do not localize}
355+
LBinaryLineBreak := EOL;
356+
End
357+
Else
358+
LLine := ReadLnRFC(VMsgEnd, LF, '.'); {do not localize}
359+
End
360+
Else
361+
Begin
362+
LLine := FFirstLine;
363+
FFirstLine := ''; {Do not Localize}
364+
FProcessFirstLine := False;
365+
// Do not use ADELIM since always ends with . (standard)
366+
If LLine = '.' Then
367+
Begin {Do not Localize}
368+
VMsgEnd := True;
369+
Break;
370+
End;
371+
If TextStartsWith(LLine, '..') Then
372+
Delete(LLine, 1, 1);
373+
End;
374+
If VMsgEnd Then
375+
Break;
376+
If MIMEBoundary <> '' Then
428377
Begin
429-
If LDecoder Is TRESTDWDecoderBinHex4 Then
378+
If TextIsSame(LLine, LBoundaryStart) Then
379+
Begin
380+
Result := TRESTDWMessageDecoderMIME.Create(Owner);
381+
Break;
382+
End;
383+
If TextIsSame(LLine, LBoundaryEnd) Then
430384
Begin
431-
//Now decode the complete block...
432-
LDecoder.Decode(LBuffer);
385+
If Owner is TRESTDWMessage Then
386+
TRESTDWMessage(Owner).MIMEBoundary.Pop;
387+
Break;
433388
End;
434-
LDecoder.DecodeEnd;
435389
End;
436-
Finally
437-
FreeAndNil(LDecoder);
438-
End;
390+
If LDecoder = Nil Then
391+
Begin
392+
If LIsBinaryContentTransferEncoding Then
393+
Begin {do not localize}
394+
If LIsThisTheFirstLine Then
395+
LIsThisTheFirstLine := False
396+
Else
397+
Begin
398+
If Assigned(ADestStream) Then
399+
WriteStringToStream(ADestStream, LBinaryLineBreak, -1, 1);
400+
End;
401+
If Assigned(ADestStream) Then
402+
WriteStringToStream(ADestStream, LLine, -1, 1);
403+
End
404+
Else
405+
Begin
406+
If Assigned(ADestStream) Then
407+
WriteStringToStream(ADestStream, LLine + EOL, -1, 1);
408+
End;
409+
End
410+
Else
411+
Begin
412+
If LDecoder Is TRESTDWDecoderQuotedPrintable Then
413+
LDecoder.Decode(LLine + EOL)
414+
Else If LDecoder Is TRESTDWDecoderBinHex4 Then
415+
LBuffer := LBuffer + LLine
416+
Else If LLine <> '' Then
417+
LDecoder.Decode(LLine);
418+
End;
419+
Until False;
420+
If LDecoder <> Nil Then
421+
Begin
422+
If LDecoder Is TRESTDWDecoderBinHex4 Then
423+
LDecoder.Decode(LBuffer);
424+
LDecoder.DecodeEnd;
425+
End;
426+
Finally
427+
FreeAndNil(LDecoder);
428+
End;
439429
End;
440430

441431
Function TRESTDWMessageDecoderMIME.GetAttachmentFilename(Const AContentType,
@@ -565,11 +555,6 @@ destructor TRESTDWMessageDecoderMIME.Destroy;
565555
FMessageEncoderClass := TRESTDWMessageEncoderMIME;
566556
End;
567557

568-
destructor TRESTDWMessageEncoderInfoMIME.Destroy;
569-
begin
570-
Inherited;
571-
end;
572-
573558
Procedure TRESTDWMessageEncoderInfoMIME.InitializeHeaders(AMsg : TRESTDWMessage);
574559
Begin
575560
If AMsg.ContentType = '' Then

0 commit comments

Comments
 (0)