jio 0.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,26 @@
1
+ #ifndef JIO_TRANSACTION_H
2
+ #define JIO_TRANSACTION_H
3
+
4
+ #define JIO_TRANSACTION_RELEASED 0x01
5
+
6
+ typedef struct {
7
+ jtrans_t *trans;
8
+ VALUE views;
9
+ int flags;
10
+ } jio_jtrans_wrapper;
11
+
12
+ #define JioAssertTransaction(obj) JioAssertType(obj, rb_cJioTransaction, "JIO::Transaction")
13
+ #define JioGetTransaction(obj) \
14
+ jio_jtrans_wrapper *trans = NULL; \
15
+ JioAssertTransaction(obj); \
16
+ Data_Get_Struct(obj, jio_jtrans_wrapper, trans); \
17
+ if (!trans) rb_raise(rb_eTypeError, "uninitialized JIO transaction handle!");
18
+
19
+ void rb_jio_mark_transaction(void *ptr);
20
+ void rb_jio_free_transaction(void *ptr);
21
+
22
+ VALUE rb_jio_file_new_transaction(VALUE obj, VALUE flags);
23
+
24
+ void _init_rb_jio_transaction();
25
+
26
+ #endif
Binary file
@@ -0,0 +1,22 @@
1
+ # encoding: utf-8
2
+
3
+ require File.expand_path('../lib/jio/version', __FILE__)
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "jio"
7
+ s.version = JIO::VERSION
8
+ s.summary = "jio - transactional, journaled file I/O for Ruby"
9
+ s.description = "jio - transactional, journaled file I/O for Ruby"
10
+ s.authors = ["Lourens Naudé"]
11
+ s.email = ["lourens@methodmissing.com"]
12
+ s.homepage = "http://github.com/methodmissing/jio"
13
+ s.date = Time.now.utc.strftime('%Y-%m-%d')
14
+ s.platform = Gem::Platform::RUBY
15
+ s.extensions = Dir["ext/jio/extconf.rb"]
16
+ s.has_rdoc = true
17
+ s.files = `git ls-files`.split
18
+ s.test_files = `git ls-files test`.split("\n")
19
+ s.rdoc_options = ["--charset=UTF-8"]
20
+ s.require_paths = ["lib"]
21
+ s.add_development_dependency('rake-compiler', '~> 0.8.1')
22
+ end
@@ -0,0 +1,12 @@
1
+ # encoding: utf-8
2
+
3
+ begin
4
+ require "jio/jio_ext"
5
+ rescue LoadError
6
+ require "jio_ext"
7
+ end
8
+
9
+ module JIO
10
+ end
11
+
12
+ require 'jio/file'
@@ -0,0 +1,24 @@
1
+ # encoding: utf-8
2
+
3
+ module JIO
4
+ class File
5
+ alias orig_transaction transaction
6
+ def transaction(flags)
7
+ if block_given?
8
+ begin
9
+ trans = orig_transaction(flags)
10
+ yield trans
11
+ rescue
12
+ trans.rollback
13
+ error = true
14
+ raise
15
+ ensure
16
+ trans.commit if !error && !trans.committed?
17
+ trans.release
18
+ end
19
+ else
20
+ orig_transaction(flags)
21
+ end
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,5 @@
1
+ # encoding: utf-8
2
+
3
+ module JIO
4
+ VERSION = '0.1'
5
+ end
@@ -0,0 +1,32 @@
1
+ # encoding: utf-8
2
+
3
+ require 'test/unit'
4
+ require 'jio'
5
+ require 'fileutils' #19
6
+ require 'timeout'
7
+
8
+ TMP = File.expand_path(File.join(File.dirname(__FILE__), '..', 'tmp'))
9
+ SANDBOX = File.join(TMP, 'sandbox')
10
+ FileUtils.rm_rf SANDBOX
11
+ FileUtils.mkdir_p SANDBOX
12
+
13
+ class JioTestCase < Test::Unit::TestCase
14
+ FILE = File.join(SANDBOX, 'file.jio')
15
+ OPEN_ARGS = [FILE, JIO::RDWR | JIO::CREAT | JIO::TRUNC, 0644, JIO::J_LINGER]
16
+
17
+ undef_method :default_test if method_defined? :default_test
18
+
19
+ def setup
20
+ File.unlink(FILE) if File.exists?(FILE)
21
+ end
22
+
23
+ if ENV['STRESS_GC']
24
+ def setup
25
+ GC.stress = true
26
+ end
27
+
28
+ def teardown
29
+ GC.stress = false
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,116 @@
1
+ # encoding: utf-8
2
+
3
+ require File.join(File.dirname(__FILE__), 'helper')
4
+
5
+ class TestFile < JioTestCase
6
+ def test_open_close
7
+ file = JIO.open(*OPEN_ARGS)
8
+ assert_instance_of JIO::File, file
9
+ ensure
10
+ assert file.close
11
+ end
12
+
13
+ def test_sync
14
+ file = JIO.open(*OPEN_ARGS)
15
+ assert file.sync
16
+ ensure
17
+ assert file.close
18
+ end
19
+
20
+ def test_move_journal
21
+ file = JIO.open(*OPEN_ARGS)
22
+ assert file.move_journal(SANDBOX)
23
+ ensure
24
+ assert file.close
25
+ end
26
+
27
+ def test_autosync
28
+ file = JIO.open(*OPEN_ARGS)
29
+ assert file.autosync(1, 1024)
30
+ file.write("CO")
31
+ file.write("MM")
32
+ file.write("IT")
33
+ sleep 1.1
34
+ file.rewind
35
+ assert_equal "COMMIT", file.read(6)
36
+ assert file.stop_autosync
37
+ ensure
38
+ assert file.close
39
+ end
40
+
41
+ def test_read_write
42
+ file = JIO.open(*OPEN_ARGS)
43
+ assert_equal "", file.read(0)
44
+ assert_equal 4, file.write('ABCD')
45
+ assert_equal 'ABCD', file.pread(4, 0)
46
+ file.pwrite('EFGH', 4)
47
+ assert_equal 'EFGH', file.pread(4, 4)
48
+ file.pwrite('LMNOPQRS', 0)
49
+ assert_equal 'LMNOPQRS', file.pread(8, 0)
50
+ ensure
51
+ assert file.close
52
+ end
53
+
54
+ def test_lseek
55
+ file = JIO.open(*OPEN_ARGS)
56
+ assert_equal 4, file.write('ABCD')
57
+ file.lseek(2, IO::SEEK_SET)
58
+ assert_equal 'CD', file.read(2)
59
+ ensure
60
+ assert file.close
61
+ end
62
+
63
+ def test_truncate
64
+ file = JIO.open(*OPEN_ARGS)
65
+ assert_equal 4, file.write('ABCD')
66
+ assert_equal 4, File.size(FILE)
67
+ file.truncate(2)
68
+ assert_equal 2, File.size(FILE)
69
+ file.truncate(0)
70
+ assert_equal 0, File.size(FILE)
71
+ ensure
72
+ assert file.close
73
+ end
74
+
75
+ def test_fileno
76
+ file = JIO.open(*OPEN_ARGS)
77
+ assert_instance_of Fixnum, file.fileno
78
+ ensure
79
+ assert file.close
80
+ end
81
+
82
+ def test_rewind
83
+ file = JIO.open(*OPEN_ARGS)
84
+ file.write('ABCD')
85
+ file.rewind
86
+ assert_equal 'ABCD', file.read(4)
87
+ ensure
88
+ assert file.close
89
+ end
90
+
91
+ def test_tell
92
+ file = JIO.open(*OPEN_ARGS)
93
+ file.write('ABCD')
94
+ assert_equal 4, file.tell
95
+ ensure
96
+ assert file.close
97
+ end
98
+
99
+ def test_eof_p
100
+ file = JIO.open(*OPEN_ARGS)
101
+ file.write('ABCD')
102
+ assert file.eof?
103
+ file.rewind
104
+ assert !file.eof?
105
+ ensure
106
+ assert file.close
107
+ end
108
+
109
+ def test_error
110
+ file = JIO.open(*OPEN_ARGS)
111
+ file.write('ABCD')
112
+ assert !file.error?
113
+ ensure
114
+ assert file.close
115
+ end
116
+ end
@@ -0,0 +1,23 @@
1
+ # encoding: utf-8
2
+
3
+ require File.join(File.dirname(__FILE__), 'helper')
4
+
5
+ class TestJio < JioTestCase
6
+ def test_check
7
+ file = JIO.open(*OPEN_ARGS)
8
+ trans = file.transaction(JIO::J_LINGER)
9
+ trans.write('COMMIT', 0)
10
+ assert trans.commit
11
+ assert trans.committed?
12
+ expected = {:reapplied=>1,
13
+ :invalid=>2,
14
+ :corrupt=>0,
15
+ :total=>3,
16
+ :in_progress=>0,
17
+ :broken=>0}
18
+ assert_equal expected, JIO.check(FILE, 0)
19
+ ensure
20
+ trans.release
21
+ assert file.close
22
+ end
23
+ end
@@ -0,0 +1,111 @@
1
+ # encoding: utf-8
2
+
3
+ require File.join(File.dirname(__FILE__), 'helper')
4
+
5
+ class TestTransaction < JioTestCase
6
+ def test_spawn_transaction
7
+ file = JIO.open(*OPEN_ARGS)
8
+ trans = file.transaction(JIO::J_LINGER)
9
+ assert_instance_of JIO::Transaction, trans
10
+ ensure
11
+ trans.release
12
+ assert file.close
13
+ end
14
+
15
+ def test_spawn_transaction_with_block
16
+ file = JIO.open(*OPEN_ARGS)
17
+ file.transaction(JIO::J_LINGER) do |trans|
18
+ assert_instance_of JIO::Transaction, trans
19
+ trans.write("COMMIT", 0)
20
+ end
21
+ assert_equal "COMMIT", file.read(6)
22
+ ensure
23
+ assert file.close
24
+ end
25
+
26
+ def test_spawn_transaction_with_block_error
27
+ file = JIO.open(*OPEN_ARGS)
28
+ file.transaction(JIO::J_LINGER) do |trans|
29
+ assert_instance_of JIO::Transaction, trans
30
+ trans.write("COMMIT", 0)
31
+ raise "rollback"
32
+ end rescue nil
33
+ assert_not_equal "COMMIT", file.read(6)
34
+ ensure
35
+ assert file.close
36
+ end
37
+
38
+ def test_transaction_views
39
+ file = JIO.open(*OPEN_ARGS)
40
+ trans = file.transaction(JIO::J_LINGER)
41
+ trans.write('COMMIT', 0)
42
+ trans.read(2, 2)
43
+ assert_equal [], trans.views
44
+ assert_equal nil, trans.release
45
+ ensure
46
+ assert file.close
47
+ end
48
+
49
+ def test_commit_transaction
50
+ file = JIO.open(*OPEN_ARGS)
51
+ trans = file.transaction(JIO::J_LINGER)
52
+ trans.write('COMMIT', 0)
53
+ trans.read(2, 2)
54
+ trans.read(2, 4)
55
+ assert_equal [], trans.views
56
+ assert trans.commit
57
+ assert_equal %w(MM IT), trans.views
58
+ ensure
59
+ trans.release
60
+ file.close
61
+ end
62
+
63
+ def test_rollback_transaction
64
+ file = JIO.open(*OPEN_ARGS)
65
+ trans = file.transaction(JIO::J_LINGER)
66
+ trans.write('COMMIT', 0)
67
+ assert trans.commit
68
+ assert trans.rollback
69
+ ensure
70
+ trans.release
71
+ assert file.close
72
+ end
73
+
74
+ def test_transaction_committed_p
75
+ file = JIO.open(*OPEN_ARGS)
76
+ trans = file.transaction(JIO::J_LINGER)
77
+ trans.write('COMMIT', 0)
78
+ assert trans.commit
79
+ assert trans.committed?
80
+ ensure
81
+ trans.release
82
+ assert file.close
83
+ end
84
+
85
+
86
+ def test_transaction_rollbacked_p
87
+ file = JIO.open(*OPEN_ARGS)
88
+ trans = file.transaction(JIO::J_LINGER)
89
+ trans.write('COMMIT', 0)
90
+ assert trans.commit
91
+ assert_equal 'COMMIT', file.read(6)
92
+ assert trans.rollback
93
+ # XXX: try to reproduce a rollbacked state
94
+ assert !trans.rollbacked?
95
+ ensure
96
+ trans.release
97
+ assert file.close
98
+ end
99
+
100
+ def test_transaction_rollbacking_p
101
+ file = JIO.open(*OPEN_ARGS)
102
+ trans = file.transaction(JIO::J_LINGER)
103
+ trans.write('COMMIT', 0)
104
+ assert trans.commit
105
+ assert trans.rollback
106
+ assert !trans.rollbacking?
107
+ ensure
108
+ trans.release
109
+ assert file.close
110
+ end
111
+ end
metadata ADDED
@@ -0,0 +1,90 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: jio
3
+ version: !ruby/object:Gem::Version
4
+ version: '0.1'
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Lourens Naudé
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-08-02 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: rake-compiler
16
+ requirement: &70330249254420 !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ~>
20
+ - !ruby/object:Gem::Version
21
+ version: 0.8.1
22
+ type: :development
23
+ prerelease: false
24
+ version_requirements: *70330249254420
25
+ description: jio - transactional, journaled file I/O for Ruby
26
+ email:
27
+ - lourens@methodmissing.com
28
+ executables: []
29
+ extensions:
30
+ - ext/jio/extconf.rb
31
+ extra_rdoc_files: []
32
+ files:
33
+ - .gitignore
34
+ - .travis.yml
35
+ - Gemfile
36
+ - Gemfile.lock
37
+ - LICENSE
38
+ - README.rdoc
39
+ - Rakefile
40
+ - ext/jio/extconf.rb
41
+ - ext/jio/file.c
42
+ - ext/jio/file.h
43
+ - ext/jio/jio_ext.c
44
+ - ext/jio/jio_ext.h
45
+ - ext/jio/jio_prelude.h
46
+ - ext/jio/jruby.h
47
+ - ext/jio/rubinius.h
48
+ - ext/jio/ruby18.h
49
+ - ext/jio/ruby19.h
50
+ - ext/jio/transaction.c
51
+ - ext/jio/transaction.h
52
+ - ext/libjio.tar.gz
53
+ - jio.gemspec
54
+ - lib/jio.rb
55
+ - lib/jio/file.rb
56
+ - lib/jio/version.rb
57
+ - test/helper.rb
58
+ - test/test_file.rb
59
+ - test/test_jio.rb
60
+ - test/test_transaction.rb
61
+ homepage: http://github.com/methodmissing/jio
62
+ licenses: []
63
+ post_install_message:
64
+ rdoc_options:
65
+ - --charset=UTF-8
66
+ require_paths:
67
+ - lib
68
+ required_ruby_version: !ruby/object:Gem::Requirement
69
+ none: false
70
+ requirements:
71
+ - - ! '>='
72
+ - !ruby/object:Gem::Version
73
+ version: '0'
74
+ required_rubygems_version: !ruby/object:Gem::Requirement
75
+ none: false
76
+ requirements:
77
+ - - ! '>='
78
+ - !ruby/object:Gem::Version
79
+ version: '0'
80
+ requirements: []
81
+ rubyforge_project:
82
+ rubygems_version: 1.8.10
83
+ signing_key:
84
+ specification_version: 3
85
+ summary: jio - transactional, journaled file I/O for Ruby
86
+ test_files:
87
+ - test/helper.rb
88
+ - test/test_file.rb
89
+ - test/test_jio.rb
90
+ - test/test_transaction.rb