tataru 0.1.0 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Gemfile +5 -0
- data/bin/console +15 -0
- data/bin/setup +8 -0
- data/lib/tataru.rb +70 -12
- data/lib/tataru/base_resource.rb +49 -0
- data/lib/tataru/base_resource_desc.rb +35 -0
- data/lib/tataru/compiler.rb +100 -0
- data/lib/tataru/create_subroutines.rb +31 -0
- data/lib/tataru/delete_subroutines.rb +42 -0
- data/lib/tataru/flattener.rb +81 -0
- data/lib/tataru/init_hash_compiler.rb +41 -0
- data/lib/tataru/instruction.rb +52 -7
- data/lib/tataru/instruction_hash.rb +54 -0
- data/lib/tataru/instructions/call_instruction.rb +19 -0
- data/lib/tataru/instructions/check_create_instruction.rb +27 -0
- data/lib/tataru/instructions/check_delete_instruction.rb +20 -0
- data/lib/tataru/instructions/check_instruction.rb +26 -0
- data/lib/tataru/instructions/check_update_instruction.rb +27 -0
- data/lib/tataru/instructions/clear_instruction.rb +12 -0
- data/lib/tataru/instructions/compare_instruction.rb +16 -0
- data/lib/tataru/instructions/create_instruction.rb +20 -0
- data/lib/tataru/instructions/delete_instruction.rb +14 -0
- data/lib/tataru/instructions/end_instruction.rb +12 -0
- data/lib/tataru/instructions/goto_if_instruction.rb +26 -0
- data/lib/tataru/instructions/immediate_mode_instruction.rb +12 -0
- data/lib/tataru/instructions/init_instruction.rb +27 -0
- data/lib/tataru/instructions/key_instruction.rb +12 -0
- data/lib/tataru/instructions/mark_deletable_instruction.rb +13 -0
- data/lib/tataru/instructions/read_instruction.rb +28 -0
- data/lib/tataru/instructions/rescmp_instruction.rb +34 -0
- data/lib/tataru/instructions/resource_instruction.rb +15 -0
- data/lib/tataru/instructions/return_instruction.rb +16 -0
- data/lib/tataru/instructions/update_instruction.rb +16 -0
- data/lib/tataru/instructions/value_instruction.rb +15 -0
- data/lib/tataru/instructions/value_rom_instruction.rb +23 -0
- data/lib/tataru/instructions/value_update_instruction.rb +18 -0
- data/lib/tataru/memory.rb +16 -0
- data/lib/tataru/quest.rb +43 -0
- data/lib/tataru/representation.rb +22 -0
- data/lib/tataru/representations/array_representation.rb +18 -0
- data/lib/tataru/representations/hash_representation.rb +20 -0
- data/lib/tataru/representations/literal_representation.rb +9 -0
- data/lib/tataru/representations/output_representation.rb +19 -0
- data/lib/tataru/representations/resource_representation.rb +49 -0
- data/lib/tataru/resolver.rb +39 -0
- data/lib/tataru/resource_dsl.rb +21 -71
- data/lib/tataru/resource_type_pool.rb +22 -0
- data/lib/tataru/rom_reader.rb +47 -0
- data/lib/tataru/runner.rb +48 -0
- data/lib/tataru/sub_planner.rb +41 -0
- data/lib/tataru/subroutine_compiler.rb +52 -0
- data/lib/tataru/top_dsl.rb +35 -0
- data/lib/tataru/update_subroutines.rb +111 -0
- data/lib/tataru/version.rb +1 -1
- data/spec/compiler_spec.rb +181 -0
- data/spec/flattener_spec.rb +88 -0
- data/spec/init_hash_compiler_spec.rb +85 -0
- data/spec/instruction_hash_spec.rb +63 -0
- data/spec/instruction_spec.rb +36 -0
- data/spec/instructions/call_instruction_spec.rb +28 -0
- data/spec/instructions/check_create_instruction_spec.rb +67 -0
- data/spec/instructions/check_delete_instruction_spec.rb +47 -0
- data/spec/instructions/check_update_instruction_spec.rb +67 -0
- data/spec/instructions/clear_instruction_spec.rb +16 -0
- data/spec/instructions/compare_instruction_spec.rb +29 -0
- data/spec/instructions/create_instruction_spec.rb +62 -0
- data/spec/instructions/delete_instruction_spec.rb +20 -0
- data/spec/instructions/end_instruction_spec.rb +15 -0
- data/spec/instructions/goto_if_instruction_spec.rb +42 -0
- data/spec/instructions/init_instruction_spec.rb +16 -0
- data/spec/instructions/key_instruction_spec.rb +15 -0
- data/spec/instructions/mark_deletable_instruction_spec.rb +20 -0
- data/spec/instructions/read_instruction_spec.rb +34 -0
- data/spec/instructions/rescmp_instruction_spec.rb +113 -0
- data/spec/instructions/return_instruction_spec.rb +28 -0
- data/spec/instructions/update_instruction_spec.rb +39 -0
- data/spec/instructions/value_instruction_spec.rb +27 -0
- data/spec/instructions/value_rom_instruction_spec.rb +170 -0
- data/spec/instructions/value_update_instruction_spec.rb +35 -0
- data/spec/quest_spec.rb +9 -0
- data/spec/representations/array_representation_spec.rb +29 -0
- data/spec/representations/hash_representation_spec.rb +29 -0
- data/spec/representations/literal_representation_spec.rb +10 -0
- data/spec/representations/output_representation_spec.rb +11 -0
- data/spec/representations/resource_representation_spec.rb +50 -0
- data/spec/resource_dsl_spec.rb +71 -0
- data/spec/runner_spec.rb +99 -0
- data/spec/spec_helper.rb +401 -0
- data/spec/subroutine_compiler_spec.rb +39 -0
- data/spec/taru_spec.rb +616 -0
- data/spec/top_dsl_spec.rb +68 -0
- data/tataru.gemspec +45 -0
- metadata +145 -27
- data/Rakefile +0 -8
- data/lib/tataru/default_resource_finder.rb +0 -10
- data/lib/tataru/execution_step.rb +0 -79
- data/lib/tataru/planner.rb +0 -93
- data/lib/tataru/requirements.rb +0 -67
- data/lib/tataru/requirements_dsl.rb +0 -33
- data/lib/tataru/resource.rb +0 -52
- data/lib/tataru/state.rb +0 -64
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a3fcccc4e7437ee62c60032204c2c0fccb36291e0ffdd240021fb2248e4e8b62
|
4
|
+
data.tar.gz: 0432c564d3338a05984e50cc57ef59085273a935ad32882d48f1ba6611e9a53f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fcaa6f65aaa656d8933901ba3bc8257b6ef41a78b6ec9b2ffd25efd1e2f283c250349ea079019ba4f34ba92e553af22ba1c17e61a84fddc8cdc9de305c8639f6
|
7
|
+
data.tar.gz: c3d436483365f80eecb90247dfafc149fddfb56ead3376db15ebe4485291aa72aaca5e5bf89ae3a85b24e57835ba81c9575176c55c13d4ce39b2981394b85fae
|
data/Gemfile
ADDED
data/bin/console
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# frozen_string_literal: true
|
3
|
+
|
4
|
+
require 'bundler/setup'
|
5
|
+
require 'binrip'
|
6
|
+
|
7
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
8
|
+
# with your gem easier. You can also use a different console, if you like.
|
9
|
+
|
10
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
11
|
+
# require "pry"
|
12
|
+
# Pry.start
|
13
|
+
|
14
|
+
require 'irb'
|
15
|
+
IRB.start(__FILE__)
|
data/bin/setup
ADDED
data/lib/tataru.rb
CHANGED
@@ -1,15 +1,73 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require '
|
4
|
-
require '
|
5
|
-
|
6
|
-
require 'tataru/
|
7
|
-
require 'tataru/resource'
|
8
|
-
require 'tataru/state'
|
9
|
-
require 'tataru/instruction'
|
10
|
-
require 'tataru/execution_step'
|
11
|
-
require 'tataru/planner'
|
12
|
-
require 'tataru/default_resource_finder'
|
13
|
-
require 'tataru/requirements_dsl'
|
3
|
+
require 'tataru/rom_reader'
|
4
|
+
require 'tataru/base_resource'
|
5
|
+
require 'tataru/base_resource_desc'
|
6
|
+
require 'tataru/representation'
|
14
7
|
require 'tataru/resource_dsl'
|
15
|
-
require 'tataru/
|
8
|
+
require 'tataru/resolver'
|
9
|
+
require 'tataru/top_dsl'
|
10
|
+
require 'tataru/flattener'
|
11
|
+
require 'tataru/create_subroutines'
|
12
|
+
require 'tataru/delete_subroutines'
|
13
|
+
require 'tataru/update_subroutines'
|
14
|
+
require 'tataru/subroutine_compiler'
|
15
|
+
require 'tataru/init_hash_compiler'
|
16
|
+
require 'tataru/sub_planner'
|
17
|
+
require 'tataru/compiler'
|
18
|
+
require 'tataru/quest'
|
19
|
+
require 'tataru/resource_type_pool'
|
20
|
+
require 'tataru/instruction_hash'
|
21
|
+
require 'tataru/instruction'
|
22
|
+
require 'tataru/memory'
|
23
|
+
require 'tataru/runner'
|
24
|
+
|
25
|
+
module Tataru
|
26
|
+
# Entry class
|
27
|
+
class Taru
|
28
|
+
def initialize(rtp, current_state = {}, &block)
|
29
|
+
@rtp = rtp
|
30
|
+
@current_state = current_state
|
31
|
+
@quest = Tataru::Quest.new(rtp, current_state)
|
32
|
+
@quest.construct(&block)
|
33
|
+
@ih = Tataru::InstructionHash.new(@quest.instr_hash)
|
34
|
+
@runner = Tataru::Runner.new(@ih.instruction_list)
|
35
|
+
end
|
36
|
+
|
37
|
+
def step
|
38
|
+
@runner.run_next
|
39
|
+
!@runner.ended?
|
40
|
+
end
|
41
|
+
|
42
|
+
def oplog
|
43
|
+
@runner.oplog
|
44
|
+
end
|
45
|
+
|
46
|
+
def error
|
47
|
+
@runner.memory.error
|
48
|
+
end
|
49
|
+
|
50
|
+
def state
|
51
|
+
@runner.memory.hash[:remote_ids].map do |k, v|
|
52
|
+
extract_state(k, v)
|
53
|
+
end.to_h
|
54
|
+
end
|
55
|
+
|
56
|
+
def extract_state(key, value)
|
57
|
+
if key.start_with? '_deletable_'
|
58
|
+
original_key = key.sub(/^_deletable_/, '')
|
59
|
+
[key, {
|
60
|
+
name: value,
|
61
|
+
desc: @current_state[original_key][:desc],
|
62
|
+
dependencies: @current_state[original_key][:dependencies]
|
63
|
+
}]
|
64
|
+
else
|
65
|
+
[key, {
|
66
|
+
name: value,
|
67
|
+
desc: @quest.dsl.resources[key].desc.class.name,
|
68
|
+
dependencies: @quest.dsl.dep_graph[key]
|
69
|
+
}]
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Tataru
|
4
|
+
# base class of resource
|
5
|
+
class BaseResource
|
6
|
+
attr_reader :remote_id
|
7
|
+
|
8
|
+
def initialize(remote_id)
|
9
|
+
@remote_id = remote_id
|
10
|
+
end
|
11
|
+
|
12
|
+
def create(_name_value_hash)
|
13
|
+
# create the resource
|
14
|
+
end
|
15
|
+
|
16
|
+
def read(_name_array)
|
17
|
+
# read a range of resource fields
|
18
|
+
{}
|
19
|
+
end
|
20
|
+
|
21
|
+
def update(name_value_hash)
|
22
|
+
# update the resource fields
|
23
|
+
end
|
24
|
+
|
25
|
+
def delete
|
26
|
+
# delete the resource
|
27
|
+
end
|
28
|
+
|
29
|
+
def outputs
|
30
|
+
# resource outputs
|
31
|
+
{}
|
32
|
+
end
|
33
|
+
|
34
|
+
def create_complete?
|
35
|
+
# check if creation is complete
|
36
|
+
true
|
37
|
+
end
|
38
|
+
|
39
|
+
def update_complete?
|
40
|
+
# check if update is complete
|
41
|
+
true
|
42
|
+
end
|
43
|
+
|
44
|
+
def delete_complete?
|
45
|
+
# check if delete is complete
|
46
|
+
true
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Tataru
|
4
|
+
# description of a resource
|
5
|
+
class BaseResourceDesc
|
6
|
+
def resource_class
|
7
|
+
# returns the class of the resource
|
8
|
+
BaseResource
|
9
|
+
end
|
10
|
+
|
11
|
+
def mutable_fields
|
12
|
+
[] # fields that can be passed in to create and update
|
13
|
+
end
|
14
|
+
|
15
|
+
def immutable_fields
|
16
|
+
[] # fields that cannot be passed in to update but can be passed to create
|
17
|
+
end
|
18
|
+
|
19
|
+
def output_fields
|
20
|
+
[] # fields that cannot be passed in to create or update
|
21
|
+
end
|
22
|
+
|
23
|
+
def required_fields
|
24
|
+
[] # mutable or immutable fields that cannot be omitted
|
25
|
+
end
|
26
|
+
|
27
|
+
def needs_remote_id?
|
28
|
+
false # true if resource requires a remote id
|
29
|
+
end
|
30
|
+
|
31
|
+
def delete_at_end?
|
32
|
+
false # if true moves deletes to end of program
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,100 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'bunny/tsort'
|
4
|
+
|
5
|
+
module Tataru
|
6
|
+
# compiler
|
7
|
+
class Compiler
|
8
|
+
def initialize(dsl, extant_resources = {}, extant_dependencies = {})
|
9
|
+
@dsl = dsl
|
10
|
+
@extant = extant_resources
|
11
|
+
@extant_dependencies = extant_dependencies
|
12
|
+
end
|
13
|
+
|
14
|
+
def instr_hash
|
15
|
+
{
|
16
|
+
init: {
|
17
|
+
**InitHashCompiler.new(@dsl).result,
|
18
|
+
labels: labels
|
19
|
+
},
|
20
|
+
instructions: top_instructions + subroutine_instructions
|
21
|
+
}
|
22
|
+
end
|
23
|
+
|
24
|
+
def labels
|
25
|
+
@labels ||= generate_labels
|
26
|
+
end
|
27
|
+
|
28
|
+
def subroutines
|
29
|
+
@subroutines ||= generate_subroutines
|
30
|
+
end
|
31
|
+
|
32
|
+
def top_instructions
|
33
|
+
@top_instructions ||= [
|
34
|
+
:init,
|
35
|
+
*generate_top_instructions,
|
36
|
+
:end
|
37
|
+
]
|
38
|
+
end
|
39
|
+
|
40
|
+
def subroutine_instructions
|
41
|
+
@subroutine_instructions ||=
|
42
|
+
subroutines.values.flat_map(&:body_instructions)
|
43
|
+
end
|
44
|
+
|
45
|
+
def generate_labels
|
46
|
+
count = 0
|
47
|
+
subroutines.values.map do |sub|
|
48
|
+
arr = [sub.label, top_instructions.count + count]
|
49
|
+
count += sub.body_instructions.count
|
50
|
+
arr
|
51
|
+
end.to_h
|
52
|
+
end
|
53
|
+
|
54
|
+
def deletables
|
55
|
+
@extant.reject { |k, _| @dsl.resources.key? k }
|
56
|
+
end
|
57
|
+
|
58
|
+
def updatables
|
59
|
+
@dsl.resources
|
60
|
+
end
|
61
|
+
|
62
|
+
def generate_subroutines
|
63
|
+
result = {}
|
64
|
+
# set up resources for deletion
|
65
|
+
deletables.each do |k, v|
|
66
|
+
desc = Tataru.const_get(v).new
|
67
|
+
rrep = Representations::ResourceRepresentation.new(k, desc, {})
|
68
|
+
sp = SubPlanner.new(rrep, :delete)
|
69
|
+
result.merge!(sp.subroutines)
|
70
|
+
end
|
71
|
+
|
72
|
+
# set up resources for updates or creates
|
73
|
+
updatables.each do |k, rrep|
|
74
|
+
action = @extant.key?(k) ? :update : :create
|
75
|
+
sp = SubPlanner.new(rrep, action)
|
76
|
+
result.merge!(sp.subroutines)
|
77
|
+
end
|
78
|
+
result
|
79
|
+
end
|
80
|
+
|
81
|
+
def generate_step_order(order, steps)
|
82
|
+
instructions = []
|
83
|
+
order.each do |level|
|
84
|
+
steps.each do |step|
|
85
|
+
instructions += level.map do |item|
|
86
|
+
subroutines["#{item}_#{step}"].call_instruction
|
87
|
+
end
|
88
|
+
end
|
89
|
+
end
|
90
|
+
instructions
|
91
|
+
end
|
92
|
+
|
93
|
+
def generate_top_instructions
|
94
|
+
order = Bunny::Tsort.tsort(@extant_dependencies.merge(@dsl.dep_graph))
|
95
|
+
|
96
|
+
generate_step_order(order, %i[start check]) +
|
97
|
+
generate_step_order(order.reverse, %i[commit finish])
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Tataru
|
4
|
+
# create subroutines
|
5
|
+
module CreateSubroutines
|
6
|
+
def create_instructions
|
7
|
+
@rrep.check_required_fields!
|
8
|
+
[
|
9
|
+
*load_resource_instructions,
|
10
|
+
{ key: :properties },
|
11
|
+
{ value_rom: @rrep.name },
|
12
|
+
:create
|
13
|
+
]
|
14
|
+
end
|
15
|
+
|
16
|
+
def check_create_instructions
|
17
|
+
[
|
18
|
+
*load_resource_instructions,
|
19
|
+
:check_create
|
20
|
+
]
|
21
|
+
end
|
22
|
+
|
23
|
+
def commit_create_instructions
|
24
|
+
[]
|
25
|
+
end
|
26
|
+
|
27
|
+
def finish_create_instructions
|
28
|
+
[]
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Tataru
|
4
|
+
# delete subroutines
|
5
|
+
module DeleteSubroutines
|
6
|
+
def delete_instructions
|
7
|
+
return [] if desc.delete_at_end?
|
8
|
+
|
9
|
+
[
|
10
|
+
*load_resource_instructions,
|
11
|
+
:delete
|
12
|
+
]
|
13
|
+
end
|
14
|
+
|
15
|
+
def check_delete_instructions
|
16
|
+
return [] if desc.delete_at_end?
|
17
|
+
|
18
|
+
[
|
19
|
+
*load_resource_instructions,
|
20
|
+
:check_delete
|
21
|
+
]
|
22
|
+
end
|
23
|
+
|
24
|
+
def commit_delete_instructions
|
25
|
+
return [] unless desc.delete_at_end?
|
26
|
+
|
27
|
+
[
|
28
|
+
*load_resource_instructions,
|
29
|
+
:delete
|
30
|
+
]
|
31
|
+
end
|
32
|
+
|
33
|
+
def finish_delete_instructions
|
34
|
+
return [] unless desc.delete_at_end?
|
35
|
+
|
36
|
+
[
|
37
|
+
*load_resource_instructions,
|
38
|
+
:check_delete
|
39
|
+
]
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,81 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Tataru
|
4
|
+
# flattens properties to make them digestable
|
5
|
+
class Flattener
|
6
|
+
def initialize(value)
|
7
|
+
@value = value
|
8
|
+
@result = {}
|
9
|
+
end
|
10
|
+
|
11
|
+
def flattened
|
12
|
+
flatten(@value, :top)
|
13
|
+
@result
|
14
|
+
end
|
15
|
+
|
16
|
+
def flatten(value, name)
|
17
|
+
type = value.class.name
|
18
|
+
.sub(/^Tataru::Representations::/, '')
|
19
|
+
.sub(/Representation$/, '')
|
20
|
+
.downcase
|
21
|
+
method_name = :"flatten_#{type}"
|
22
|
+
raise "cannot flatten #{value.inspect}" unless respond_to?(method_name)
|
23
|
+
|
24
|
+
send(method_name, value, name)
|
25
|
+
end
|
26
|
+
|
27
|
+
def flatten_literal(value, name)
|
28
|
+
@result[name] = {
|
29
|
+
type: :literal,
|
30
|
+
value: value.value
|
31
|
+
}
|
32
|
+
end
|
33
|
+
|
34
|
+
def flatten_array(value, name)
|
35
|
+
refs = {}
|
36
|
+
value.value.each_with_index do |val, i|
|
37
|
+
key = :"#{name}_#{i}"
|
38
|
+
flatten(val, key)
|
39
|
+
refs[i] = key
|
40
|
+
end
|
41
|
+
@result[name] = {
|
42
|
+
type: :array,
|
43
|
+
references: refs
|
44
|
+
}
|
45
|
+
end
|
46
|
+
|
47
|
+
def flatten_hash(value, name)
|
48
|
+
refs = {}
|
49
|
+
value.value.each do |k, v|
|
50
|
+
key = :"#{name}_#{k}"
|
51
|
+
flatten(v, key)
|
52
|
+
refs[k] = key
|
53
|
+
end
|
54
|
+
@result[name] = {
|
55
|
+
type: :hash,
|
56
|
+
references: refs
|
57
|
+
}
|
58
|
+
end
|
59
|
+
|
60
|
+
def flatten_resource(value, name)
|
61
|
+
refs = {}
|
62
|
+
value.properties.each do |k, v|
|
63
|
+
key = :"#{name}_#{k}"
|
64
|
+
flatten(v, key)
|
65
|
+
refs[k] = key
|
66
|
+
end
|
67
|
+
@result[name] = {
|
68
|
+
type: :hash,
|
69
|
+
references: refs
|
70
|
+
}
|
71
|
+
end
|
72
|
+
|
73
|
+
def flatten_output(value, name)
|
74
|
+
@result[name] = {
|
75
|
+
type: :output,
|
76
|
+
resource: value.resource_name,
|
77
|
+
output: value.output_field_name
|
78
|
+
}
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|