eco-helpers 2.5.1 → 2.5.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +52 -1
- data/eco-helpers.gemspec +2 -2
- data/lib/eco/api/common/loaders/parser.rb +0 -1
- data/lib/eco/api/common/loaders/use_case.rb +0 -2
- data/lib/eco/api/common/people/person_entry_attribute_mapper.rb +0 -2
- data/lib/eco/api/common/session/logger.rb +22 -77
- data/lib/eco/api/microcases/with_each.rb +0 -1
- data/lib/eco/api/organization/tag_tree.rb +64 -15
- data/lib/eco/api/session/config/tagtree.rb +32 -10
- data/lib/eco/api/session/config/workflow.rb +9 -3
- data/lib/eco/api/session/config.rb +6 -2
- data/lib/eco/api/session.rb +2 -2
- data/lib/eco/api/usecases/default_cases/abstract_policygroup_abilities_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/analyse_people_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/append_usergroups_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/change_email_case.rb +1 -2
- data/lib/eco/api/usecases/default_cases/clean_unknown_tags_case.rb +0 -5
- data/lib/eco/api/usecases/default_cases/clear_abilities_case.rb +2 -2
- data/lib/eco/api/usecases/default_cases/codes_to_tags_case.rb +5 -7
- data/lib/eco/api/usecases/default_cases/create_case.rb +0 -5
- data/lib/eco/api/usecases/default_cases/create_details_case.rb +0 -5
- data/lib/eco/api/usecases/default_cases/create_details_with_supervisor_case.rb +0 -5
- data/lib/eco/api/usecases/default_cases/csv_to_tree_case/helper.rb +1 -1
- data/lib/eco/api/usecases/default_cases/csv_to_tree_case.rb +0 -4
- data/lib/eco/api/usecases/default_cases/delete_sync_case.rb +2 -4
- data/lib/eco/api/usecases/default_cases/delete_trans_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/email_as_id_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/entries_to_csv_case.rb +0 -4
- data/lib/eco/api/usecases/default_cases/hris_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/new_email_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/new_id_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/org_data_convert_case.rb +0 -5
- data/lib/eco/api/usecases/default_cases/refresh_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/reinvite_sync_case.rb +1 -3
- data/lib/eco/api/usecases/default_cases/reinvite_trans_case.rb +2 -2
- data/lib/eco/api/usecases/default_cases/remove_account_sync_case.rb +1 -2
- data/lib/eco/api/usecases/default_cases/remove_account_trans_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/reset_landing_page_case.rb +1 -7
- data/lib/eco/api/usecases/default_cases/restore_db_case.rb +0 -10
- data/lib/eco/api/usecases/default_cases/set_default_tag_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/set_supervisor_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/supers_cyclic_identify_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/supers_hierarchy_case.rb +2 -3
- data/lib/eco/api/usecases/default_cases/switch_supervisor_case.rb +2 -4
- data/lib/eco/api/usecases/default_cases/tagtree_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/to_csv_case.rb +4 -5
- data/lib/eco/api/usecases/default_cases/to_csv_detailed_case.rb +0 -1
- data/lib/eco/api/usecases/default_cases/transfer_account_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/update_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/update_details_case.rb +0 -2
- data/lib/eco/api/usecases/default_cases/upsert_case.rb +0 -4
- data/lib/eco/api/usecases/graphql/base.rb +6 -18
- data/lib/eco/api/usecases/graphql/helpers/base.rb +31 -0
- data/lib/eco/api/usecases/graphql/helpers/location/base.rb +87 -0
- data/lib/eco/api/usecases/graphql/helpers/location/command/result.rb +69 -0
- data/lib/eco/api/usecases/graphql/helpers/location/command/results.rb +126 -0
- data/lib/eco/api/usecases/graphql/helpers/location/command.rb +84 -0
- data/lib/eco/api/usecases/graphql/helpers/location.rb +7 -0
- data/lib/eco/api/usecases/graphql/helpers.rb +2 -1
- data/lib/eco/api/usecases/graphql/samples/location/command/dsl.rb +54 -0
- data/lib/eco/api/usecases/graphql/samples/location/command/results.rb +125 -0
- data/lib/eco/api/usecases/graphql/samples/location/command.rb +10 -0
- data/lib/eco/api/usecases/graphql/samples/location/dsl.rb +6 -0
- data/lib/eco/api/usecases/graphql/samples/location.rb +10 -0
- data/lib/eco/api/usecases/graphql/samples.rb +6 -0
- data/lib/eco/api/usecases/graphql.rb +2 -1
- data/lib/eco/api/usecases/ooze_cases/export_register_case.rb +0 -1
- data/lib/eco/api/usecases/ooze_samples/ooze_base_case.rb +0 -2
- data/lib/eco/api/usecases/ooze_samples/register_migration_case.rb +0 -2
- data/lib/eco/api/usecases/use_case.rb +2 -2
- data/lib/eco/cli/config/default/workflow.rb +3 -5
- data/lib/eco/cli/scripting/args_helpers.rb +0 -2
- data/lib/eco/csv/table.rb +39 -3
- data/lib/eco/data/files/helpers.rb +1 -0
- data/lib/eco/data/hashes/array_diff.rb +12 -6
- data/lib/eco/data/hashes/diff_result.rb +1 -2
- data/lib/eco/data/locations/convert.rb +92 -0
- data/lib/eco/data/locations/dsl.rb +35 -0
- data/lib/eco/data/locations/node_base/builder.rb +26 -0
- data/lib/eco/data/locations/node_base/csv_convert.rb +57 -0
- data/lib/eco/data/locations/node_base/parsing.rb +30 -0
- data/lib/eco/data/locations/node_base/serial.rb +26 -0
- data/lib/eco/data/locations/node_base/tag_validations.rb +52 -0
- data/lib/eco/data/locations/node_base/treeify.rb +150 -0
- data/lib/eco/data/locations/node_base.rb +48 -0
- data/lib/eco/data/locations/node_level/builder.rb +6 -0
- data/lib/eco/data/locations/node_level/cleaner.rb +74 -0
- data/lib/eco/data/locations/node_level/parsing.rb +63 -0
- data/lib/eco/data/locations/node_level/serial.rb +37 -0
- data/lib/eco/data/locations/node_level.rb +156 -0
- data/lib/eco/data/locations/node_plain/builder.rb +6 -0
- data/lib/eco/data/locations/node_plain/parsing.rb +36 -0
- data/lib/eco/data/locations/node_plain/serial.rb +14 -0
- data/lib/eco/data/locations/node_plain.rb +34 -0
- data/lib/eco/data/locations.rb +12 -0
- data/lib/eco/data.rb +1 -0
- data/lib/eco/language/auxiliar_logger.rb +9 -1
- data/lib/eco/language/basic_logger.rb +74 -0
- data/lib/eco/language.rb +2 -1
- data/lib/eco/version.rb +1 -1
- metadata +37 -8
- data/lib/eco/api/usecases/default_cases/new_id_case0.rb +0 -14
- data/lib/eco/api/usecases/graphql/helpers/locations/commands.rb +0 -4
- data/lib/eco/api/usecases/graphql/helpers/locations.rb +0 -6
@@ -0,0 +1,74 @@
|
|
1
|
+
class Eco::Data::Locations::NodeLevel
|
2
|
+
module Cleaner
|
3
|
+
include Eco::Language::AuxiliarLogger
|
4
|
+
include Eco::Data::Locations::Convert
|
5
|
+
|
6
|
+
# Prevents repeated node ids/tags, decouples merged levels,
|
7
|
+
# covers gaps (jumping multiple levels)
|
8
|
+
# @note
|
9
|
+
# 1. It first discards node ids/tags that have been already pulled (discard repeated)
|
10
|
+
# 2. For non repeated, it identifies if there's a gap (jump of multiple levels)
|
11
|
+
# 3. It covers the gap if present by decoupling merged parent(s) from the same node (see node.decouple)
|
12
|
+
# 4. Then, it delegates the filling in of parents to `fill_in_parents` function.
|
13
|
+
# @return [Array<NodeLevel>] child to parent relationships solved and no double-ups.
|
14
|
+
def tidy_nodes(nodes, prev_level: 0, main: true)
|
15
|
+
reset_trackers! if main
|
16
|
+
nodes.each_with_object([]) do |node, out|
|
17
|
+
node_id = node.id
|
18
|
+
if done_ids.include?(node_id)
|
19
|
+
repeated_ids << "#{node_id} (level: #{node.level})"
|
20
|
+
else
|
21
|
+
level = node.actual_level
|
22
|
+
if level > prev_level + 1
|
23
|
+
gap = level - (prev_level + 1)
|
24
|
+
msg = "(Row: #{node.row_num}) ID/Tag '#{node_id}' (lev #{level}) jumps #{gap} level(s) (expected #{prev_level + 1})."
|
25
|
+
#puts " " + node.tags_array.pretty_inspect
|
26
|
+
missing_nodes = node.decouple(gap)
|
27
|
+
|
28
|
+
msg << "\n Adding missing upper level(s): " + missing_nodes.map(&:raw_tag).pretty_inspect
|
29
|
+
log(:info) { msg }
|
30
|
+
|
31
|
+
out.push(*tidy_nodes(missing_nodes, prev_level: prev_level, main: false))
|
32
|
+
# puts node.actual_level
|
33
|
+
# pp node.tags_array
|
34
|
+
level = prev_level + 1
|
35
|
+
end
|
36
|
+
out << node
|
37
|
+
done_ids << node_id
|
38
|
+
prev_level = level
|
39
|
+
end
|
40
|
+
end.yield_self do |out|
|
41
|
+
report_repeated_node_ids(repeated_ids) if main
|
42
|
+
fill_in_parents(out)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
# Sets the `parentId` property.
|
47
|
+
def fill_in_parents(nodes)
|
48
|
+
nodes.tap do |nodes|
|
49
|
+
prev_nodes = empty_level_tracker_hash(11)
|
50
|
+
nodes.each do |node|
|
51
|
+
if parent_node = prev_nodes[node.actual_level - 1]
|
52
|
+
node.parentId = parent_node.id
|
53
|
+
end
|
54
|
+
prev_nodes[node.raw_level] = node
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
# Tracker helper (those repeated)
|
60
|
+
def repeated_ids
|
61
|
+
@repeated_ids ||= []
|
62
|
+
end
|
63
|
+
|
64
|
+
# Tracker helper (those done)
|
65
|
+
def done_ids
|
66
|
+
@done_ids ||= []
|
67
|
+
end
|
68
|
+
|
69
|
+
def reset_trackers!
|
70
|
+
@done_ids = []
|
71
|
+
@repeated_ids = []
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
@@ -0,0 +1,63 @@
|
|
1
|
+
class Eco::Data::Locations::NodeLevel
|
2
|
+
module Parsing
|
3
|
+
include Eco::Data::Locations::NodeLevel::Cleaner
|
4
|
+
include Eco::Data::Locations::Convert
|
5
|
+
|
6
|
+
attr_writer :node_class
|
7
|
+
|
8
|
+
def node_class
|
9
|
+
@node_class ||= Eco::Data::Locations::NodeLevel
|
10
|
+
end
|
11
|
+
|
12
|
+
# It evaluates as an opposite to `NodePlain`
|
13
|
+
# @note there are only two accepted input csv formats.
|
14
|
+
# The expected header of `NodePlain` is predictable,
|
15
|
+
# but the header of `NodeLevel` is not.
|
16
|
+
# @param [CSV::Table]
|
17
|
+
# @return [Boolean] whether or not it's worthy trying to parse with `NodeLevel`.
|
18
|
+
def csv_matches_format?(csv)
|
19
|
+
return false unless csv.is_a?(::CSV::Table)
|
20
|
+
!Eco::Data::Locations::NodePlain.csv_matches_format?(csv)
|
21
|
+
end
|
22
|
+
|
23
|
+
# @note
|
24
|
+
# 1. It ensures basic data integrity when builing the nodes in the first screening
|
25
|
+
# 2. It then delegates the tidy up to a cleaner function (see `tidy_nodes`)
|
26
|
+
# @param `csv` [CSV::Table]
|
27
|
+
# @return [Array<NodeLevel>]
|
28
|
+
def nodes_from_csv(csv)
|
29
|
+
raise ArgumentError, "Expecting CSV::Table. Given: #{csv.class}" unless csv.is_a?(::CSV::Table)
|
30
|
+
|
31
|
+
prev_level = nil
|
32
|
+
prev_node = nil
|
33
|
+
prev_nodes = empty_level_tracker_hash(11)
|
34
|
+
|
35
|
+
# Convert to Eco::CSV::Table for a fresh start
|
36
|
+
csv = Eco::CSV.parse(csv.to_csv).nil_blank_cells.add_index_column(:row_num)
|
37
|
+
|
38
|
+
nodes = csv.each_with_object([]) do |row, out|
|
39
|
+
row_num, *values = row.fields
|
40
|
+
node = node_class.new(row_num, *values)
|
41
|
+
prev_node ||= node
|
42
|
+
|
43
|
+
# If node is nested in prev_node or is a sibling thereof
|
44
|
+
if prev_node.raw_level <= node.raw_level
|
45
|
+
# Make sure parent is among upper level tags
|
46
|
+
node.set_high_levels(prev_node)
|
47
|
+
else
|
48
|
+
if parent_node = prev_nodes[node.raw_level - 1]
|
49
|
+
node.set_high_levels(parent_node)
|
50
|
+
elsif node.raw_level == 1
|
51
|
+
# It is expected not to have parent (as it's top level tag)
|
52
|
+
else
|
53
|
+
raise "Node '#{node.raw_tag}' (#{node.row_num} row) doesn't have parent"
|
54
|
+
end
|
55
|
+
end
|
56
|
+
out << node
|
57
|
+
prev_nodes[node.raw_level] = node
|
58
|
+
prev_node = node
|
59
|
+
end
|
60
|
+
tidy_nodes(nodes)
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
class Eco::Data::Locations::NodeLevel
|
2
|
+
module Serial
|
3
|
+
include Eco::Data::Locations::NodeLevel::Cleaner
|
4
|
+
include Eco::Data::Locations::Convert
|
5
|
+
|
6
|
+
attr_writer :serializer
|
7
|
+
|
8
|
+
# @return [Proc] the serializer to be used.
|
9
|
+
def serializer
|
10
|
+
@serializer ||= proc do |node|
|
11
|
+
raise "Expecting NodeLevel. Given: #{node.class}" unless node.is_a?(Eco::Data::Locations::NodeLevel)
|
12
|
+
keys = %w[row_num id name]
|
13
|
+
keys.zip(node.values_at(*keys)).to_h.tap do |out|
|
14
|
+
out['parent_id'] = node.parentId
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
# Transforms `nodes` into a **hierarchical** csv tree.
|
20
|
+
# @note
|
21
|
+
# 1. `tidy_nodes` is called out of consistency. For example,
|
22
|
+
# it might be that the parents are not set. After this call,
|
23
|
+
# all the integrity issues have been warned.
|
24
|
+
# 2. `NodeBase` has this same class method. This one was kept
|
25
|
+
# to preserve its indepenence towards treeify.
|
26
|
+
# @return [CSV::Table] ready to dump into a hierarhical **csv** (columns are tree levels)
|
27
|
+
def nodes_to_csv_tree(nodes)
|
28
|
+
tidy_nodes(nodes).each_with_object([]) do |node, out|
|
29
|
+
out << (row = empty_array(node.actual_level))
|
30
|
+
# replace last item with `node.id`
|
31
|
+
row[-1..-1] = [node.id]
|
32
|
+
end.tap do |out|
|
33
|
+
return Eco::CSV::Table.new(normalize_arrays(out))
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,156 @@
|
|
1
|
+
module Eco::Data::Locations
|
2
|
+
NODE_LEVEL_ATTRS = %i[row_num l1 l2 l3 l4 l5 l6 l7 l8 l9 l10 l11]
|
3
|
+
NodeLevelStruct = Struct.new(*NODE_LEVEL_ATTRS)
|
4
|
+
# Class to treat input csv in a form of levels, where each column is one level,
|
5
|
+
# and children are placed in higher columns right below the parent.
|
6
|
+
class NodeLevel < NodeLevelStruct
|
7
|
+
include Eco::Data::Locations::NodeBase
|
8
|
+
|
9
|
+
require_relative 'node_level/cleaner'
|
10
|
+
require_relative 'node_level/parsing'
|
11
|
+
require_relative 'node_level/serial'
|
12
|
+
require_relative 'node_level/builder'
|
13
|
+
extend Eco::Data::Locations::NodeLevel::Builder
|
14
|
+
|
15
|
+
ALL_ATTRS = NODE_LEVEL_ATTRS
|
16
|
+
ADDITIONAL_ATTRS = %i[row_num]
|
17
|
+
TAGS_ATTRS = ALL_ATTRS - ADDITIONAL_ATTRS
|
18
|
+
|
19
|
+
attr_accessor :parentId
|
20
|
+
|
21
|
+
def nodeId
|
22
|
+
id
|
23
|
+
end
|
24
|
+
|
25
|
+
def id
|
26
|
+
tag.upcase
|
27
|
+
end
|
28
|
+
|
29
|
+
def name
|
30
|
+
tag
|
31
|
+
end
|
32
|
+
|
33
|
+
def tag
|
34
|
+
clean_id(raw_tag)
|
35
|
+
end
|
36
|
+
|
37
|
+
def raw_tag
|
38
|
+
values_at(*TAGS_ATTRS.reverse).compact.first
|
39
|
+
end
|
40
|
+
|
41
|
+
def level
|
42
|
+
actual_level
|
43
|
+
end
|
44
|
+
|
45
|
+
def actual_level
|
46
|
+
tags_array.compact.length
|
47
|
+
end
|
48
|
+
|
49
|
+
def raw_level
|
50
|
+
tags_array.index(raw_tag) + 1
|
51
|
+
end
|
52
|
+
|
53
|
+
def tag_idx
|
54
|
+
tags_array.index(raw_tag)
|
55
|
+
end
|
56
|
+
|
57
|
+
def previous_idx
|
58
|
+
idx = tag_idx - 1
|
59
|
+
idx < 0 ? nil : idx
|
60
|
+
end
|
61
|
+
|
62
|
+
def empty_idx
|
63
|
+
tary = tags_array
|
64
|
+
tary.index(nil) || tary.length + 1
|
65
|
+
end
|
66
|
+
|
67
|
+
# We got a missing level that is compacted in one row
|
68
|
+
# Here we get the missing intermediate levels
|
69
|
+
# This is done from upper to lower level to ensure processing order
|
70
|
+
# It skips last one, as that is this object already
|
71
|
+
def decouple(num = 1)
|
72
|
+
with_info = filled_idxs
|
73
|
+
# must be the last among filled_idxs, so let's use it to verify
|
74
|
+
unless with_info.last == tag_idx
|
75
|
+
raise "Review this (row #{row_num}; '#{raw_tag}'): tag_idx is #{tag_idx}, while last filled idx is #{with_info.last}"
|
76
|
+
end
|
77
|
+
len = with_info.length
|
78
|
+
target_idxs = with_info[len-(num+1)..-2]
|
79
|
+
target_idxs.map do |idx|
|
80
|
+
self.copy.tap do |dup|
|
81
|
+
dup.clear_level(idx_to_level(idx + 1))
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def merge!(node)
|
87
|
+
override_upper_levels(node.tags_array)
|
88
|
+
end
|
89
|
+
|
90
|
+
def set_high_levels(node)
|
91
|
+
override_lower_levels(node.tags_array)
|
92
|
+
end
|
93
|
+
|
94
|
+
def clear_level(i)
|
95
|
+
case i
|
96
|
+
when Enumerable
|
97
|
+
target = i.to_a
|
98
|
+
when Integer
|
99
|
+
return false unless i >= 1 && i <= tag_attrs_count
|
100
|
+
target = Array(i..tag_attrs_count)
|
101
|
+
else
|
102
|
+
return false
|
103
|
+
end
|
104
|
+
return false if target.empty?
|
105
|
+
target.each do |n|
|
106
|
+
#puts "clearing 'l#{n}': #{attr("l#{n}")}"
|
107
|
+
set_attr("l#{n}", nil)
|
108
|
+
end
|
109
|
+
true
|
110
|
+
end
|
111
|
+
|
112
|
+
def override_upper_levels(src_tags_array, from_level: self.raw_level + 1)
|
113
|
+
target_lev = Array(from_level..tag_attrs_count)
|
114
|
+
target_tags = src_tags_array[level_to_idx(from_level)..level_to_idx(tag_attrs_count)]
|
115
|
+
target_lev.zip(target_tags).each do |(n, tag)|
|
116
|
+
set_attr("l#{n}", tag)
|
117
|
+
end
|
118
|
+
self
|
119
|
+
end
|
120
|
+
|
121
|
+
def override_lower_levels(src_tags_array, to_level: self.raw_level - 1)
|
122
|
+
target_lev = Array(1..to_level)
|
123
|
+
target_tags = src_tags_array[level_to_idx(1)..level_to_idx(to_level)]
|
124
|
+
target_lev.zip(target_tags).each do |(n, tag)|
|
125
|
+
set_attr("l#{n}", tag)
|
126
|
+
end
|
127
|
+
self
|
128
|
+
end
|
129
|
+
|
130
|
+
def idx_to_level(x)
|
131
|
+
x + 1
|
132
|
+
end
|
133
|
+
|
134
|
+
def level_to_idx(x)
|
135
|
+
x - 1
|
136
|
+
end
|
137
|
+
|
138
|
+
def filled_idxs
|
139
|
+
tags_array.each_with_index.with_object([]) do |(tg, ix), out|
|
140
|
+
out << ix if tg
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
def blanks_between?
|
145
|
+
actual_level > empty_idx
|
146
|
+
end
|
147
|
+
|
148
|
+
def tags_array
|
149
|
+
values_at(*TAGS_ATTRS)
|
150
|
+
end
|
151
|
+
|
152
|
+
def tag_attrs_count
|
153
|
+
TAGS_ATTRS.length
|
154
|
+
end
|
155
|
+
end
|
156
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
class Eco::Data::Locations::NodePlain
|
2
|
+
module Parsing
|
3
|
+
attr_writer :node_class
|
4
|
+
|
5
|
+
def node_class
|
6
|
+
@node_class ||= Eco::Data::Locations::NodePlain
|
7
|
+
end
|
8
|
+
|
9
|
+
# Subset of property names expected to be among the headers
|
10
|
+
def basic_headers
|
11
|
+
@expected_headers ||= %w[id name parent_id]
|
12
|
+
end
|
13
|
+
|
14
|
+
# Checks if the `basic_headers` to process as `NodePlain` are present.
|
15
|
+
# @param [CSV::Table]
|
16
|
+
# @return [Boolean] whether or not it's worthy trying to parse with `NodePlain`.
|
17
|
+
def csv_matches_format?(csv)
|
18
|
+
return false unless csv.is_a?(::CSV::Table)
|
19
|
+
(basic_headers & csv.headers) == basic_headers
|
20
|
+
end
|
21
|
+
|
22
|
+
# It builds each NodePlain from the input csv.
|
23
|
+
# @param `csv` [CSV::Table]
|
24
|
+
# @return [Array<NodePlain>]
|
25
|
+
def nodes_from_csv(csv)
|
26
|
+
raise ArgumentError, "Expecting CSV::Table. Given: #{csv.class}" unless csv.is_a?(::CSV::Table)
|
27
|
+
# Convert to Eco::CSV::Table for a fresh start
|
28
|
+
csv = Eco::CSV.parse(csv.to_csv).nil_blank_cells.add_index_column(:row_num)
|
29
|
+
headers = node_class::ALL_ATTRS.map(&:to_s)
|
30
|
+
csv.each_with_object([]) do |row, out|
|
31
|
+
row_num, *values = row.values_at(*headers)
|
32
|
+
out << node_class.new(row_num, *values)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
class Eco::Data::Locations::NodePlain
|
2
|
+
module Serial
|
3
|
+
attr_writer :serializer
|
4
|
+
|
5
|
+
# @return [Proc] the serializer to be used.
|
6
|
+
def serializer
|
7
|
+
@serializer ||= proc do |node|
|
8
|
+
raise "Expecting NodePlain. Given: #{node.class}" unless node.is_a?(Eco::Data::Locations::NodePlain)
|
9
|
+
keys = Eco::Data::Locations::NodePlain::NODE_PLAIN_ATTRS
|
10
|
+
node.to_h(*keys)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
module Eco::Data::Locations
|
2
|
+
NODE_PLAIN_ATTRS = %i[row_num id name parent_id weight archived archive_token]
|
3
|
+
NodePlainStruct = Struct.new(*NODE_PLAIN_ATTRS)
|
4
|
+
# Class to treat input csv in a form of a list of nodes, where parent is specified.
|
5
|
+
class NodePlain < NodePlainStruct
|
6
|
+
include Eco::Data::Locations::NodeBase
|
7
|
+
|
8
|
+
require_relative 'node_plain/parsing'
|
9
|
+
require_relative 'node_plain/serial'
|
10
|
+
require_relative 'node_plain/builder'
|
11
|
+
extend Eco::Data::Locations::NodePlain::Builder
|
12
|
+
|
13
|
+
ALL_ATTRS = NODE_PLAIN_ATTRS
|
14
|
+
ADDITIONAL_ATTRS = %i[row_num]
|
15
|
+
PROP_ATTRS = ALL_ATTRS - ADDITIONAL_ATTRS
|
16
|
+
|
17
|
+
def id
|
18
|
+
clean_id(super)
|
19
|
+
end
|
20
|
+
|
21
|
+
def name
|
22
|
+
super || self.id
|
23
|
+
end
|
24
|
+
|
25
|
+
def parentId
|
26
|
+
self.parent_id
|
27
|
+
end
|
28
|
+
|
29
|
+
# backwards compatibility
|
30
|
+
def tag
|
31
|
+
id
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
module Eco
|
2
|
+
module Data
|
3
|
+
module Locations
|
4
|
+
end
|
5
|
+
end
|
6
|
+
end
|
7
|
+
|
8
|
+
require_relative 'locations/convert'
|
9
|
+
require_relative 'locations/node_base'
|
10
|
+
require_relative 'locations/node_plain'
|
11
|
+
require_relative 'locations/node_level'
|
12
|
+
require_relative 'locations/dsl'
|
data/lib/eco/data.rb
CHANGED
@@ -3,6 +3,9 @@ module Eco
|
|
3
3
|
# Some modules/classes use logger, but they may not be connected to session.
|
4
4
|
# This prevents errors with this.
|
5
5
|
module AuxiliarLogger
|
6
|
+
attr_writer :logger
|
7
|
+
|
8
|
+
# Provides either an available logger or a basic one
|
6
9
|
def logger
|
7
10
|
if defined?(super)
|
8
11
|
super
|
@@ -11,9 +14,14 @@ module Eco
|
|
11
14
|
elsif instance_variable_defined?(:@session)
|
12
15
|
@session.logger
|
13
16
|
else
|
14
|
-
@logger ||= ::
|
17
|
+
@logger ||= Eco::Language::BasicLogger.new
|
15
18
|
end
|
16
19
|
end
|
20
|
+
|
21
|
+
# Shortcut to logger.
|
22
|
+
def log(level, &block)
|
23
|
+
logger.send(level, &block) if logger
|
24
|
+
end
|
17
25
|
end
|
18
26
|
end
|
19
27
|
end
|
@@ -0,0 +1,74 @@
|
|
1
|
+
module Eco
|
2
|
+
module Language
|
3
|
+
# Basic logger to format messaging to console
|
4
|
+
class BasicLogger
|
5
|
+
class << self
|
6
|
+
def forward(*meths)
|
7
|
+
meths.each do |meth|
|
8
|
+
define_method(meth) do |*args, **kargs, &block|
|
9
|
+
forward(meth, *args, **kargs, &block)
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
TIMESTAMP_PATTERN = '%Y-%m-%dT%H:%M:%S'.freeze
|
16
|
+
LOG_LEVELS = %i[unknown fatal error warn info debug].freeze
|
17
|
+
METHODS = %i[<< close add].freeze
|
18
|
+
|
19
|
+
attr_writer :timestamp
|
20
|
+
attr_reader :level
|
21
|
+
|
22
|
+
forward *LOG_LEVELS, *METHODS
|
23
|
+
|
24
|
+
def initialize(level: ::Logger::INFO, timestamp: false)
|
25
|
+
@level = level
|
26
|
+
self.timestamp = timestamp
|
27
|
+
loggers[:console] = ::Logger.new(STDOUT).tap do |logger|
|
28
|
+
logger.formatter = format_proc(console: true)
|
29
|
+
logger.level = level
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def timestamp?
|
34
|
+
@timestamp
|
35
|
+
end
|
36
|
+
|
37
|
+
def level=(value)
|
38
|
+
loggers[:console].level = value
|
39
|
+
end
|
40
|
+
|
41
|
+
private
|
42
|
+
|
43
|
+
def forward(meth, *args, &block)
|
44
|
+
loggers.each do |_key, logger|
|
45
|
+
logger.send(meth, *args, &block)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def loggers
|
50
|
+
@loggers ||= {}
|
51
|
+
end
|
52
|
+
|
53
|
+
def console_timestamp(datetime)
|
54
|
+
return nil unless timestamp?
|
55
|
+
timestamp(datetime)
|
56
|
+
end
|
57
|
+
|
58
|
+
def timestamp(datetime)
|
59
|
+
return nil unless datetime
|
60
|
+
str_date = datetime.strftime(self.class::TIMESTAMP_PATTERN)
|
61
|
+
"#{str_date} > "
|
62
|
+
end
|
63
|
+
|
64
|
+
def format_proc(console: true, &block)
|
65
|
+
proc do |severity, datetime, progname, msg|
|
66
|
+
str_stamp = console ? console_timestamp(datetime) : timestamp(datetime)
|
67
|
+
"#{severity.to_s[0]}: #{str_stamp}#{msg}\n".tap do |formatted_msg|
|
68
|
+
block.call(severity, datetime, msg, formatted_msg) if block
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
data/lib/eco/language.rb
CHANGED
@@ -4,10 +4,11 @@ module Eco
|
|
4
4
|
end
|
5
5
|
|
6
6
|
require_relative 'language/models'
|
7
|
+
require_relative 'language/auxiliar_logger'
|
8
|
+
require_relative 'language/basic_logger'
|
7
9
|
require_relative 'language/curry'
|
8
10
|
require_relative 'language/hash_transform_modifier'
|
9
11
|
require_relative 'language/hash_transform'
|
10
12
|
require_relative 'language/values_at'
|
11
13
|
require_relative 'language/match_modifier'
|
12
14
|
require_relative 'language/match'
|
13
|
-
require_relative 'language/auxiliar_logger'
|
data/lib/eco/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: eco-helpers
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.5.
|
4
|
+
version: 2.5.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Oscar Segura
|
@@ -136,7 +136,7 @@ dependencies:
|
|
136
136
|
requirements:
|
137
137
|
- - ">="
|
138
138
|
- !ruby/object:Gem::Version
|
139
|
-
version: 1.1.
|
139
|
+
version: 1.1.3
|
140
140
|
- - "<"
|
141
141
|
- !ruby/object:Gem::Version
|
142
142
|
version: '1.2'
|
@@ -146,7 +146,7 @@ dependencies:
|
|
146
146
|
requirements:
|
147
147
|
- - ">="
|
148
148
|
- !ruby/object:Gem::Version
|
149
|
-
version: 1.1.
|
149
|
+
version: 1.1.3
|
150
150
|
- - "<"
|
151
151
|
- !ruby/object:Gem::Version
|
152
152
|
version: '1.2'
|
@@ -156,7 +156,7 @@ dependencies:
|
|
156
156
|
requirements:
|
157
157
|
- - ">="
|
158
158
|
- !ruby/object:Gem::Version
|
159
|
-
version: 0.3.
|
159
|
+
version: 0.3.8
|
160
160
|
- - "<"
|
161
161
|
- !ruby/object:Gem::Version
|
162
162
|
version: '0.4'
|
@@ -166,7 +166,7 @@ dependencies:
|
|
166
166
|
requirements:
|
167
167
|
- - ">="
|
168
168
|
- !ruby/object:Gem::Version
|
169
|
-
version: 0.3.
|
169
|
+
version: 0.3.8
|
170
170
|
- - "<"
|
171
171
|
- !ruby/object:Gem::Version
|
172
172
|
version: '0.4'
|
@@ -566,7 +566,6 @@ files:
|
|
566
566
|
- lib/eco/api/usecases/default_cases/hris_case.rb
|
567
567
|
- lib/eco/api/usecases/default_cases/new_email_case.rb
|
568
568
|
- lib/eco/api/usecases/default_cases/new_id_case.rb
|
569
|
-
- lib/eco/api/usecases/default_cases/new_id_case0.rb
|
570
569
|
- lib/eco/api/usecases/default_cases/org_data_convert_case.rb
|
571
570
|
- lib/eco/api/usecases/default_cases/refresh_case.rb
|
572
571
|
- lib/eco/api/usecases/default_cases/reinvite_sync_case.rb
|
@@ -592,8 +591,18 @@ files:
|
|
592
591
|
- lib/eco/api/usecases/graphql.rb
|
593
592
|
- lib/eco/api/usecases/graphql/base.rb
|
594
593
|
- lib/eco/api/usecases/graphql/helpers.rb
|
595
|
-
- lib/eco/api/usecases/graphql/helpers/
|
596
|
-
- lib/eco/api/usecases/graphql/helpers/
|
594
|
+
- lib/eco/api/usecases/graphql/helpers/base.rb
|
595
|
+
- lib/eco/api/usecases/graphql/helpers/location.rb
|
596
|
+
- lib/eco/api/usecases/graphql/helpers/location/base.rb
|
597
|
+
- lib/eco/api/usecases/graphql/helpers/location/command.rb
|
598
|
+
- lib/eco/api/usecases/graphql/helpers/location/command/result.rb
|
599
|
+
- lib/eco/api/usecases/graphql/helpers/location/command/results.rb
|
600
|
+
- lib/eco/api/usecases/graphql/samples.rb
|
601
|
+
- lib/eco/api/usecases/graphql/samples/location.rb
|
602
|
+
- lib/eco/api/usecases/graphql/samples/location/command.rb
|
603
|
+
- lib/eco/api/usecases/graphql/samples/location/command/dsl.rb
|
604
|
+
- lib/eco/api/usecases/graphql/samples/location/command/results.rb
|
605
|
+
- lib/eco/api/usecases/graphql/samples/location/dsl.rb
|
597
606
|
- lib/eco/api/usecases/ooze_cases.rb
|
598
607
|
- lib/eco/api/usecases/ooze_cases/export_register_case.rb
|
599
608
|
- lib/eco/api/usecases/ooze_samples.rb
|
@@ -662,9 +671,29 @@ files:
|
|
662
671
|
- lib/eco/data/hashes.rb
|
663
672
|
- lib/eco/data/hashes/array_diff.rb
|
664
673
|
- lib/eco/data/hashes/diff_result.rb
|
674
|
+
- lib/eco/data/locations.rb
|
675
|
+
- lib/eco/data/locations/convert.rb
|
676
|
+
- lib/eco/data/locations/dsl.rb
|
677
|
+
- lib/eco/data/locations/node_base.rb
|
678
|
+
- lib/eco/data/locations/node_base/builder.rb
|
679
|
+
- lib/eco/data/locations/node_base/csv_convert.rb
|
680
|
+
- lib/eco/data/locations/node_base/parsing.rb
|
681
|
+
- lib/eco/data/locations/node_base/serial.rb
|
682
|
+
- lib/eco/data/locations/node_base/tag_validations.rb
|
683
|
+
- lib/eco/data/locations/node_base/treeify.rb
|
684
|
+
- lib/eco/data/locations/node_level.rb
|
685
|
+
- lib/eco/data/locations/node_level/builder.rb
|
686
|
+
- lib/eco/data/locations/node_level/cleaner.rb
|
687
|
+
- lib/eco/data/locations/node_level/parsing.rb
|
688
|
+
- lib/eco/data/locations/node_level/serial.rb
|
689
|
+
- lib/eco/data/locations/node_plain.rb
|
690
|
+
- lib/eco/data/locations/node_plain/builder.rb
|
691
|
+
- lib/eco/data/locations/node_plain/parsing.rb
|
692
|
+
- lib/eco/data/locations/node_plain/serial.rb
|
665
693
|
- lib/eco/data/mapper.rb
|
666
694
|
- lib/eco/language.rb
|
667
695
|
- lib/eco/language/auxiliar_logger.rb
|
696
|
+
- lib/eco/language/basic_logger.rb
|
668
697
|
- lib/eco/language/curry.rb
|
669
698
|
- lib/eco/language/hash_transform.rb
|
670
699
|
- lib/eco/language/hash_transform_modifier.rb
|
@@ -1,14 +0,0 @@
|
|
1
|
-
class Eco::API::UseCases::DefaultCases::NewIdCase < Eco::API::Common::Loaders::UseCase
|
2
|
-
name "new-id"
|
3
|
-
type :sync
|
4
|
-
|
5
|
-
def main(entries, people, session, options, usecase)
|
6
|
-
micro = session.micro
|
7
|
-
update = session.new_job("main", "update", :update, usecase, :core)
|
8
|
-
micro.with_each_present(entries, people, options, log_starter: true) do |entry, person|
|
9
|
-
update.add(person)
|
10
|
-
person.external_id = entry.external_id
|
11
|
-
end
|
12
|
-
end
|
13
|
-
|
14
|
-
end
|