1
1
"""
2
- PyIO(x; own=false, text=missing, buflen=4096)
2
+ PyIO(x; own=false, text=missing, line_buffering=false, buflen=4096)
3
3
4
4
Wrap the Python IO stream `x` as a Julia IO stream.
5
5
@@ -10,6 +10,8 @@ If `text=true` then `x` must be a text stream and only UTF-8 must be written (i.
10
10
If `text` is not specified then it is chosen automatically.
11
11
If `x` is a text stream and you really need a binary stream, then often `PyIO(x.buffer)` will work.
12
12
13
+ If `line_buffering=true` then output is flushed at each line.
14
+
13
15
For efficiency, reads and writes are buffered before being sent to `x`.
14
16
The size of the buffers is `buflen`.
15
17
The buffers are cleared using `flush`.
@@ -20,6 +22,8 @@ mutable struct PyIO <: IO
20
22
own:: Bool
21
23
# true if `o` is text, false if binary
22
24
text:: Bool
25
+ # true to flush whenever '\n' or '\r' is encountered
26
+ line_buffering:: Bool
23
27
# true if we are definitely at the end of the file; false if we are not or don't know
24
28
eof:: Bool
25
29
# input buffer
@@ -29,7 +33,7 @@ mutable struct PyIO <: IO
29
33
obuflen:: Int
30
34
obuf:: Vector{UInt8}
31
35
32
- function PyIO (x; own:: Bool = false , text:: Union{Missing,Bool} = missing , buflen:: Integer = 4096 , ibuflen:: Integer = buflen, obuflen:: Integer = buflen)
36
+ function PyIO (x; own:: Bool = false , text:: Union{Missing,Bool} = missing , buflen:: Integer = 4096 , ibuflen:: Integer = buflen, obuflen:: Integer = buflen, line_buffering :: Bool = false )
33
37
if text === missing
34
38
text = pyhasattr (x, " encoding" )
35
39
end
@@ -39,7 +43,7 @@ mutable struct PyIO <: IO
39
43
ibuflen > 0 || error (" ibuflen must be positive" )
40
44
obuflen = convert (Int, obuflen)
41
45
obuflen > 0 || error (" obuflen must be positive" )
42
- new (Py (x), own, text, false , ibuflen, UInt8[], obuflen, UInt8[])
46
+ new (Py (x), own, text, line_buffering, false , ibuflen, UInt8[], obuflen, UInt8[])
43
47
end
44
48
end
45
49
export PyIO
@@ -136,23 +140,37 @@ Base.isopen(io::PyIO) = !pyconvert(Bool, @py io.closed)
136
140
137
141
function Base. unsafe_write (io:: PyIO , ptr:: Ptr{UInt8} , n:: UInt )
138
142
ntodo = n
139
- while true
143
+ while ntodo > 0
140
144
nroom = max (0 , io. obuflen - length (io. obuf))
141
145
if ntodo < nroom
142
- append! (io. obuf, unsafe_wrap (Array, ptr, ntodo))
143
- return n
146
+ buf = unsafe_wrap (Array, ptr, ntodo)
147
+ if io. line_buffering
148
+ i = findlast (∈ ((0x0A , 0x0D )), buf)
149
+ if i === nothing
150
+ append! (io. obuf, buf)
151
+ else
152
+ append! (io. obuf, unsafe_wrap (Array, ptr, i))
153
+ putobuf (io)
154
+ append! (io. obuf, unsafe_wrap (Array, ptr+ i, ntodo- i))
155
+ end
156
+ else
157
+ append! (io. obuf, buf)
158
+ end
159
+ break
144
160
else
145
- append! (io. obuf, unsafe_wrap (Array, ptr, nroom))
161
+ buf = unsafe_wrap (Array, ptr, nroom)
162
+ append! (io. obuf, buf)
146
163
putobuf (io)
147
164
ptr += nroom
148
165
ntodo -= nroom
149
166
end
150
167
end
168
+ return n
151
169
end
152
170
153
171
function Base. write (io:: PyIO , c:: UInt8 )
154
172
push! (io. obuf, c)
155
- if length (io. obuf) ≥ io. obuflen
173
+ if ( length (io. obuf) ≥ io. obuflen) || (io . line_buffering && (c == 0x0A || c == 0x0D ))
156
174
putobuf (io)
157
175
end
158
176
return
0 commit comments