Forum: Ruby Trouble with open/write/close cycle

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
159cd33667611645164e8623de42f67e?d=identicon&s=25 Toby DiPasquale (Guest)
on 2006-03-24 17:42
Hi all,

I'm having trouble getting an open/write/close cycle to actually put the
correct data in the file. Here's some code that illustrates the problem:

<snip>
x = "012345678\n"
10.times do
  len = 0
  begin
    len = File.stat( 'junk').size
  rescue
    len = 0
  end
  puts len.to_s
  f = File.open 'crapper', 'w'
  f.seek len
  f.write x
  f.close
end
</snip>

produces:

0
10
20
30
40
50
60
70
80
90

as output. However, the file 'junk' is filled with zeroes, except for
the last 10 bytes, which are what you'd expect them to be:

<snip>
puma:~> od -h junk
0000000 0000 0000 0000 0000 0000 0000 0000 0000
*
0000120 0000 0000 0000 0000 0000 3130 3332 3534
0000140 3736 0a38
0000144
puma:~>
</snip>

Anyone know what I'm doing wrong? I tried using sysseek and syswrite,
but I got the same results. Is Ruby's internal buffering screwing me up
here somehow? TIA.

--
Toby DiPasquale
159cd33667611645164e8623de42f67e?d=identicon&s=25 Toby DiPasquale (Guest)
on 2006-03-24 17:45
From above:

-   f = File.open 'crapper', 'w'
+    f = File.open 'junk', 'w'

Sorry.
2ffac40f8a985a2b2749244b8a1c4161?d=identicon&s=25 Mike Stok (Guest)
on 2006-03-24 17:57
(Received via mailing list)
On 24-Mar-06, at 11:43 AM, Toby DiPasquale wrote:

>   len = 0
> end
> 60
> 70
> 80
> 90
>
> as output. However, the file 'junk' is filled with zeroes, except for
> the last 10 bytes, which are what you'd expect them to be:

opening a file for writing truncates it.  Does this, opening it for
reading & writing, do what you want?

x = "012345678\n"
10.times do
   len = 0
   begin
     len = File.stat( 'junk').size
   rescue
     len = 0
   end
   puts len.to_s
   f = File.open 'junk',File::RDWR|File::CREAT
   f.seek len
   f.write x
   f.close
end

Mike

--

Mike Stok <mike@stok.ca>
http://www.stok.ca/~mike/

The "`Stok' disclaimers" apply.
23172b6630dc631a134c9bad2fec2a39?d=identicon&s=25 ChrisH (Guest)
on 2006-03-24 17:58
(Received via mailing list)
> <snip>
>     len = File.stat( 'junk').size
><snip>
>   f = File.open 'crapper', 'w'

Are there really 2 files? or is this a typo?

The docs on IO::open says tha using the 'w' mode cause the file to be
truncated if it exists.
You need to look at 'a' mode

cheers
4299e35bacef054df40583da2d51edea?d=identicon&s=25 James Gray (bbazzarrakk)
on 2006-03-24 18:02
(Received via mailing list)
On Mar 24, 2006, at 10:43 AM, Toby DiPasquale wrote:

>   begin
>     len = File.stat( 'junk').size
>   rescue
>     len = 0
>   end
>   puts len.to_s
>   f = File.open 'crapper', 'w'
>   f.seek len

The above procedure seems like a complex way to do:

File.open("junk", "a")...

Will that work for you?

James Edward Gray II
159cd33667611645164e8623de42f67e?d=identicon&s=25 Toby DiPasquale (Guest)
on 2006-03-24 18:02
Mike Stok wrote:
> opening a file for writing truncates it.

ARRRGH! I'm a moron. Of course, you are right. Thanks for the mental
clue-by-four.

--
Toby DiPasquale
159cd33667611645164e8623de42f67e?d=identicon&s=25 Toby DiPasquale (Guest)
on 2006-03-24 18:03
James Gray wrote:
> The above procedure seems like a complex way to do:
>
> File.open("junk", "a")...
>
> Will that work for you?

No, the above code was just a small example to illustrate the issue. The
real code does lots more before and after each write.

--
Toby DiPasquale
23172b6630dc631a134c9bad2fec2a39?d=identicon&s=25 ChrisH (Guest)
on 2006-03-24 18:09
(Received via mailing list)
Toby DiPasquale wrote:
> From above:
>
> -   f = File.open 'crapper', 'w'
> +    f = File.open 'junk', 'w'
>
> Sorry.

Not a problem.
When I run your snippet i get:
>ruby -w fwrite-test.rb
0
11
22
33
44
55
66
77
88
99

It looks like seeking on an empty file fills it with null data.  Not
sure if thats a Ruby thing or a feature of the underlying IO libs.

change the 'w' to an 'a' (an delete the current 'junk' file)
and the file produced looks like:
012345678
012345678
012345678
012345678
012345678
012345678
012345678
012345678
012345678
012345678


cheers
This topic is locked and can not be replied to.