asynchronous 3.0.1 → 4.0.0.pre

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- MWRlMTE2ZjM5MmYyYjRiN2I3NGIyYjJhMTdmNGY1NzcxNjMxMGJjMg==
5
- data.tar.gz: !binary |-
6
- OGNlZWE3MjliNGRhMzY3NGEzZTZkMGE4M2Q3NTExZGU0NGY0OWNhMQ==
2
+ SHA1:
3
+ metadata.gz: 8b9e12c7186a3dc906e14faede2ecab396c1d6d1
4
+ data.tar.gz: 6ce4ccbbfe6fd0bbf064e323278fec86ecd3b814
7
5
  SHA512:
8
- metadata.gz: !binary |-
9
- MTY3MmUyNTI2ODkxODMzZGEwNDdkMDI2YzY1Y2Y0MDZlOWUyOTM0NDI0MDEx
10
- YjMzN2U3NTBhNjMzNGM4Y2I1ODI1MDBhNTgyMTg2NzQ1YWM5YzM3MDhlNWIw
11
- ZDBiOTlkMjI2MTM4OTcwYTg0YjA3YWNlOTlmZGRhN2E3MWI2NzI=
12
- data.tar.gz: !binary |-
13
- NDRlMmNhODk3NDQ0YjkwNWY4MzJiNDNiMDQwZTg3YjNkNDE5Yzg3ZTQwYTRk
14
- OWNiZWRjZjg1NGMwODhmODE3OGU2NDNhYjQ5M2UwMTI4MzA2NWM4ZDc5OWRj
15
- ZTdhNmUxZTRmMDI5NmZjNmFjYWRiOTIwMGZmYjczNDgxYjU1YmM=
6
+ metadata.gz: 69ec170beaa0e9ff62e3044f25aa67f07ef42e7b6f5b1117aad5de72f907e4244a1a58039214db3ad09ac4b93149a3ee4902ed444104968daaabc67a4856e3c6
7
+ data.tar.gz: 337e7edc8238f24a442f79f33ee265fbb4d51856e9bfa755a9ae41d4f21eaea4d0d855f045a64e0b9f8e1aed1c1482e83c58efc2aa0b464fb4e26c4be20b1f3f
@@ -1,26 +1,14 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- asynchronous (2.1.0)
5
- process_shared
4
+ asynchronous (4.0.0.pre)
6
5
 
7
6
  GEM
8
7
  remote: http://rubygems.org/
9
8
  specs:
10
- columnize (0.3.6)
11
- debugger (1.6.2)
12
- columnize (>= 0.3.1)
13
- debugger-linecache (~> 1.2.0)
14
- debugger-ruby_core_source (~> 1.2.3)
15
- debugger-linecache (1.2.0)
16
- debugger-ruby_core_source (1.2.3)
17
- ffi (1.9.3)
18
- process_shared (0.2.0)
19
- ffi (~> 1.0)
20
9
 
21
10
  PLATFORMS
22
11
  ruby
23
12
 
24
13
  DEPENDENCIES
25
14
  asynchronous!
26
- debugger
data/README.md CHANGED
@@ -40,7 +40,7 @@ Like parsing (in some case)
40
40
 
41
41
  ```ruby
42
42
 
43
- calculation = async :parallelism do
43
+ thr = async :parallelism do
44
44
 
45
45
  sleep 4
46
46
  # remember, everything you
@@ -51,8 +51,8 @@ calculation = async :parallelism do
51
51
 
52
52
  end
53
53
 
54
- # to call the value (syncronize):
55
- calculation
54
+ # to call the value:
55
+ thr.value
56
56
 
57
57
  ```
58
58
 
@@ -68,74 +68,40 @@ Remember well that GarbageCollector will affect the speed.
68
68
 
69
69
  ```ruby
70
70
 
71
- calculation= async { sleep 3; 4 * 3 }
72
- # to call the value (syncronize):
73
- calculation
71
+ thr = async { sleep 3; 4 * 3 }
72
+
73
+ # to call the value:
74
+ calculation = thr.value
74
75
 
75
76
  ```
76
77
 
77
- ### Shared Memory
78
-
79
- By default the last value will be returned (OS) in IO.pipe,
80
- but when you need something else, there is the shared_memory!
81
-
82
- Shared memory is good when you want make a ruby worked on native OS thread ,
83
- but need to update data back at the mother process.
84
-
85
- the usecase is simple like that:
86
- ```ruby
87
-
88
- SharedMemory.anything_you_want_use_as_variable_name= {:some=>:object}
89
- SharedMemory.anything_you_want_use_as_variable_name #> {:some=>:object}
90
-
91
- # or
92
-
93
- shared_memory.anything_you_want_use_as_variable_name #> {:some=>:object}
94
-
95
- ```
96
-
97
- by default i set the memory allocation to 16Mb because it common usecase to me (MongoDB),
98
- but feel free to change!:
99
- ```ruby
100
-
101
- Asynchronous.memory_allocation_size= 1024 #INT!
102
-
103
- ```
104
-
105
- ## making shared memory obj static (constant)
106
-
107
- you can set a shared memory obj to be static if you dont want it to be changed later on
108
- ```ruby
109
- shared_memory.test_value= Array.new.push(:something)
110
- Asynchronous.static_variables.push :test_value
111
- shared_memory.test_value= Array.new #> this wont happen
112
- ```
113
-
114
-
115
78
  ### Example
116
79
 
117
- ```ruby
118
-
119
- # you can use simple :p or :parallelism as nametag
120
- # remember :parallelism is all about real OS thread case, so
121
- # you CANT modify the objects in memory only in sharedmemories,
122
- # the normal variables will only be copy on write modify
123
- # This is ideal for big operations where you need do a big process
124
- # w/o the fear of the Garbage collector slowness or the GIL lock
125
- # when you need to update objects in the memory use SharedMemory
126
- #
127
- # Remember! if the hardware only got 1 cpu, it will be like a harder
128
- # to use concurrency with an expensive memory allocation
129
- calculation = async :OS do
80
+ you can use simple :p or :parallelism as nametag
81
+ remember :parallelism is all about real OS thread case,
82
+ so you CANT modify the objects in the memory,
83
+ the normal variables will only be copy on write modify
130
84
 
131
- sleep 4
132
- 4 * 5
85
+ This is ideal for big operations where you need do a big process
86
+ w/o the fear of the Garbage collector slowness or the GIL lock
87
+ when you need to update objects in the memory use SharedMemory
133
88
 
134
- end
89
+ Remember! if the hardware only got 1 cpu, it will be like a harder
90
+ to use concurrency with an expensive memory allocation
135
91
 
136
- calculation += 1
92
+ ```ruby
137
93
 
138
- puts calculation
94
+ thr = async :OS do
95
+
96
+ sleep 4
97
+ 4 * 5
98
+
99
+ end
100
+
101
+ calculation = thr.value
102
+ calculation += 1
103
+
104
+ puts calculation
139
105
 
140
106
  ```
141
107
 
@@ -145,32 +111,15 @@ there are other examples that you can check in the exampels folder
145
111
  ### known bugs
146
112
 
147
113
  In rare case when you get object_buffer error
148
- * use .sync method on the async variable
114
+ * use .join method on the async variable
149
115
 
150
116
  ```ruby
151
- calculation = async :OS do
152
- sleep 4
153
- 4 * 5
154
- end
155
117
 
156
- calculation.sync #> or synchronize
157
- ```
158
-
159
- Kernel holding on Native threads with pipes can choke up
160
- * direct sleep commands can do this on multiple native threads
161
- ** hard processing load not like that, only kernel sleep
162
-
163
- SharedMemory objects not updating on chain method obj manipulation
164
-
165
- ```ruby
166
- shared_memory.var= {'jobs'=>[]}
118
+ thr = async :OS do
119
+ sleep 4
120
+ 4 * 5
121
+ end
122
+
123
+ thr.join #> thr
167
124
 
168
- {'jobs'=>[]}['jobs'].push 'data' #> {'jobs'=>[]}
169
-
170
- workaround is like that:
171
-
172
- local_variable= {'jobs'=>[]}
173
- local_variable['jobs'].push('data')
174
-
175
- shared_memory.var= local_variable
176
- ```
125
+ ```
data/VERSION CHANGED
@@ -1 +1 @@
1
- 3.0.1
1
+ 4.0.0.pre
@@ -19,8 +19,4 @@ Gem::Specification.new do |spec|
19
19
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
20
20
  spec.require_paths = ["lib"]
21
21
 
22
- spec.add_dependency "process_shared"
23
- spec.add_development_dependency(%q<debugger>, [">= 0"])
24
-
25
-
26
22
  end
@@ -1,12 +1,12 @@
1
1
  # Require Gemfile gems
2
- require_relative "../lib/asynchronous"
2
+ require_relative 'bootstrap'
3
3
 
4
4
  # you can use simple :c also instead of :concurrency
5
5
  # remember :concurrency is all about GIL case, so
6
6
  # you can modify the objects in memory
7
7
  # This is ideal for little operations in simultaneously or
8
8
  # when you need to update objects in the memory
9
- calculation = async :concurrency do
9
+ thr1 = async :concurrency do
10
10
 
11
11
  sleep 2
12
12
  4 * 2
@@ -14,22 +14,24 @@ calculation = async :concurrency do
14
14
  end
15
15
  puts "hello concurrency"
16
16
 
17
- calculation += 1
17
+ calculation1 = thr1.value
18
+ calculation1 += 1
18
19
 
19
- puts calculation
20
+ puts calculation1
20
21
 
21
22
  #>--------------------------------------------------
22
23
  # or you can use simple {} without sym and this will be by default a
23
24
  # :concurrency pattern
24
25
 
25
- calculation = async { sleep 3; 4 * 3 }
26
+ thr2 = async { sleep 3; 4 * 3 }
26
27
 
27
28
  puts "hello simple concurrency"
28
29
 
29
- calculation += 1
30
+ calculation2 = thr2.value
31
+ calculation2 += 1
30
32
 
31
33
  # remember you have to use to cal the return value from the code block!
32
- puts calculation
34
+ puts calculation2
33
35
 
34
36
 
35
37
  #>--------------------------------------------------
@@ -41,7 +43,7 @@ puts calculation
41
43
  # This is ideal for big operations where you need do a big process
42
44
  # w/o the fear of the Garbage collector slowness or the GIL lock
43
45
  # when you need to update objects in the memory use SharedMemory
44
- calculation = async :parallelism do
46
+ thr3 = async :parallelism do
45
47
 
46
48
  sleep 4
47
49
  4 * 5
@@ -49,16 +51,17 @@ calculation = async :parallelism do
49
51
  end
50
52
  puts "hello parallelism"
51
53
 
52
- calculation += 1
54
+ calculation3 = thr3.value
55
+ calculation3 += 1
53
56
 
54
- puts calculation
57
+ puts calculation3
55
58
 
56
59
  #>--------------------------------------------------
57
60
 
58
61
  # more complex way
59
62
 
60
63
  puts "mixed usecase with arrays as return obj"
61
- calc1 = async :parallelism do
64
+ thr4 = async :parallelism do
62
65
 
63
66
  sleep 4
64
67
  # some big database processing brutal memory eater stuff
@@ -66,10 +69,10 @@ calc1 = async :parallelism do
66
69
 
67
70
  end
68
71
 
69
- calc2 = async {
72
+ thr5 = async {
70
73
  [5+1,"sup!"]
71
74
  }
72
75
 
73
- puts calc1 == calc2
74
- puts (calc1+calc2).inspect
76
+ puts 'calc1 is eql calc2:',thr4.value == thr5.value
77
+ puts (thr4.value+thr5.value).inspect
75
78
 
@@ -0,0 +1,2 @@
1
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__),'..','lib'))
2
+ require 'asynchronous'
@@ -1,10 +1,11 @@
1
- require_relative "../lib/asynchronous"
1
+ require_relative 'bootstrap'
2
2
 
3
- calculation = async :parallelism do
3
+ thr = async :parallelism do
4
4
 
5
5
  # Zombie!
6
6
  loop do
7
7
  sleep 1
8
+ puts "brains(#{$$})"
8
9
  end
9
10
  # inf loop
10
11
  #
@@ -13,12 +14,14 @@ end
13
14
 
14
15
  puts $$
15
16
  Thread.new do
17
+
16
18
  sleep 5
17
19
 
18
20
  # this want to demonstrate that,
19
21
  # if the main process is killed,
20
22
  # you wont leave zombies behind!
21
23
  system "kill -9 #{$$}"
24
+
22
25
  end
23
26
 
24
27
  loop do
@@ -0,0 +1,35 @@
1
+ require_relative 'bootstrap'
2
+
3
+ async1= async :OS do
4
+ 1000000*5
5
+ end
6
+
7
+ async2= async :OS do
8
+
9
+ var = ("!" * 1000000)
10
+ puts "the superHuge String length in the pipe is: #{var.length}"
11
+
12
+ var
13
+ end
14
+
15
+ async2_error= async :OS do
16
+
17
+ raise(SystemExit)
18
+ puts 'never happen, to system error happened!'
19
+
20
+ end
21
+
22
+ async3= async :OS do
23
+ 1000000*5.0
24
+ end
25
+
26
+ begin
27
+ async2_error.value
28
+ rescue Exception => ex
29
+ puts "\n",'when error happen:',ex
30
+ end
31
+
32
+ puts "\n",'result length based on string form:'
33
+ puts async1.value.to_s.length
34
+ puts async2.value.to_s.length
35
+ puts async3.value.to_s.length
@@ -0,0 +1 @@
1
+ require 'asynchronous'
@@ -1,12 +1,7 @@
1
1
  #encoding: UTF-8
2
2
  module Asynchronous
3
-
4
- require 'process_shared'
5
-
6
- require File.join(File.dirname(__FILE__),"asynchronous","clean_class")
7
- require File.join(File.dirname(__FILE__),"asynchronous","concurrency")
8
- require File.join(File.dirname(__FILE__),"asynchronous","parallelism")
9
- require File.join(File.dirname(__FILE__),"asynchronous","shared_memory")
10
- require File.join(File.dirname(__FILE__),"asynchronous","kernel")
11
-
3
+ require 'asynchronous/error'
4
+ require 'asynchronous/concurrency'
5
+ require 'asynchronous/parallelism'
6
+ require 'asynchronous/kernel'
12
7
  end
@@ -1,78 +1,44 @@
1
- module Asynchronous
2
-
3
- # you can use simple :c also instead of :concurrency
4
- # remember :concurrency is all about GIL case, so
5
- # you can modify the objects in memory
6
- # This is ideal for little operations in simultaneously or
7
- # when you need to update objects in the memory
8
- class Concurrency < Asynchronous::CleanClass
9
-
10
- def initialize callable
11
- begin
12
- @value= nil
13
- @try_count= 0
14
- @rescue_state= nil
15
- @thread ||= ::Thread.new { callable.call }
1
+ # you can use simple :c also instead of :concurrency
2
+ # remember :concurrency is all about GIL case, so
3
+ # you can modify the objects in memory
4
+ # This is ideal for little operations in simultaneously or
5
+ # when you need to update objects in the memory
6
+ class Asynchronous::Concurrency
7
+
8
+ def initialize(&block)
9
+
10
+ @rescue_state= nil
11
+ @try_count = 0
12
+
13
+ begin
14
+ @value= nil
15
+ @thread ||= ::Thread.new { block.call }
16
+ @rescue_state= nil
17
+ rescue ThreadError
18
+ @rescue_state ||= true
19
+ @try_count += 1
20
+ if 3 <= @try_count
21
+ @value= block.call
16
22
  @rescue_state= nil
17
- rescue ThreadError
18
- @rescue_state ||= true
19
- @try_count += 1
20
- if 3 <= @try_count
21
- @value= callable.call
22
- @rescue_state= nil
23
- else
24
- sleep 5
25
- retry
26
- end
23
+ else
24
+ sleep 5
25
+ retry
27
26
  end
28
27
  end
29
28
 
30
- def asynchronous_get_value
31
-
32
- if @value.nil?
33
- until @rescue_state.nil?
34
- sleep 1
35
- end
36
- @value= @thread.value
37
- end
38
-
39
- return @value
40
-
41
- end
42
-
43
- def asynchronous_set_value(obj)
44
- @value= obj
45
- end
46
- alias :asynchronous_set_value= :asynchronous_set_value
47
-
48
- def synchronize
49
- asynchronous_get_value
50
- end
51
- alias :sync :synchronize
52
-
53
- def method_missing(method, *args)
54
-
55
- new_value= asynchronous_get_value
56
-
57
- begin
58
- original_value= new_value.dup
59
- rescue ::TypeError
60
- original_value= new_value
61
- end
29
+ end
62
30
 
63
- return_value= new_value.__send__(method,*args)
64
- unless new_value == original_value
65
- asynchronous_set_value new_value
31
+ def join
32
+ if @value.nil?
33
+ until @rescue_state.nil?
34
+ sleep 1
66
35
  end
67
-
68
- return return_value
69
-
36
+ @value= @thread.value
70
37
  end
38
+ end
71
39
 
72
- #def respond_to_missing?(method, include_private = false)
73
- # value.respond_to?(method, include_private)
74
- #end
75
-
40
+ def value
41
+ join; @value
76
42
  end
77
43
 
78
44
  end