def test_get_cursor_in_a_vacuum(): g = Graph() cursor = g.get_cursor(None) assert cursor.graph is g assert cursor.first is None assert cursor.last is None
def test_bonodoo_reader_fields(self): folder = tempfile.TemporaryDirectory() filename = 'test_file.csv' value_1 = {'id': 2} value_2 = {'id': 3} read = OdooReader( model='res.users', domain=[], fields=['id'], ) with patch('xmlrpc.client.ServerProxy') as mk: mock_server = mk.return_value mock_server.login.return_value = 1 mock_server.execute_kw.return_value = [value_1, value_2] graph = Graph() graph.add_chain(read, CsvWriter(filename, fs='fs.data')) bonobo.run(graph, services={ 'fs.data': bonobo.open_fs(folder.name), 'odoo.server': self.server, }) mk.assert_called() with open(os.path.join(folder.name, filename), 'r') as f: lines = f.readlines() self.assertEqual(len(lines), 3) self.assertEqual(ast.literal_eval(lines[1]), value_1.get('id')) self.assertEqual(ast.literal_eval(lines[2]), value_2.get('id')) folder.cleanup()
def test_simple_execution_context(): graph = Graph() graph.add_chain(*chain) context = GraphExecutionContext(graph) assert len(context.nodes) == len(chain) assert not len(context.plugins) for i, node in enumerate(chain): assert context[i].wrapped is node assert not context.alive assert not context.started assert not context.stopped context.write(BEGIN, (), END) assert not context.alive assert not context.started assert not context.stopped context.start() assert context.alive assert context.started assert not context.stopped context.stop() assert not context.alive assert context.started assert context.stopped
def test_get_cursor(): g = Graph() cursor = g.get_cursor() assert cursor.graph is g assert cursor.first is BEGIN assert cursor.last is BEGIN
def test_graph_add_chain(): g = Graph() assert len(g.nodes) == 0 g.add_chain(identity, identity, identity) assert len(g.nodes) == 3 assert len(g.outputs_of(BEGIN)) == 1
def test_execution(): graph = Graph() graph.add_chain(*chain) strategy = NaiveStrategy() ctx = strategy.execute(graph) assert ctx.results == [1, 4, 9, 16, 25, 36, 49, 64, 81]
def test_connect_two_chains(): g = Graph() a1, a2, b1, b2 = get_pseudo_nodes("a1", "a2", "b1", "b2") g.add_chain(a1, a2, _input=None, _output=None) g.add_chain(b1, b2, _input=None, _output=None) assert len(g.outputs_of(a2)) == 0 g.add_chain(_input=a2, _output=b1) assert g.outputs_of(a2) == g.indexes_of(b1)
def test_cursor_usage_to_add_a_chain(): a, b, c = get_pseudo_nodes(*"abc") g = Graph() g.get_cursor() >> a >> b >> c assert len(g) == 3 assert g.outputs_of(BEGIN) == {g.index_of(a)} assert g.outputs_of(a) == {g.index_of(b)} assert g.outputs_of(b) == {g.index_of(c)} assert g.outputs_of(c) == set()
def test_empty_execution_context(): graph = Graph() ctx = GraphExecutionContext(graph) assert not len(ctx.nodes) assert not len(ctx.plugins) assert not ctx.alive
def test_copy(): g1 = Graph() g2 = g1.copy() assert g1 is not g2 assert len(g1) == 0 assert len(g2) == 0 g1.add_chain([]) assert len(g1) == 1 assert len(g2) == 0 g2.add_chain([], identity) assert len(g1) == 1 assert len(g2) == 2
def test_invalid_graph_usage(): g = Graph() foo, bar = get_pseudo_nodes("foo", "bar") with pytest.raises(ValueError): g.add_chain() g.add_node(foo) g.add_node(bar) with pytest.raises(RuntimeError): g.add_chain(_input=bar, _output=foo, _name="this_is_not_possible")
def test_add_branch_inbetween(): a, b, c, d, e, f = get_pseudo_nodes(6) g = Graph() c0 = g.orphan() >> a >> b c1 = g.orphan() >> c >> d c2 = g.orphan() >> e >> f c3 = c0 >> c1 >> c2 assert c0.range == g.indexes_of(a, b, _type=tuple) assert c1.range == g.indexes_of(c, d, _type=tuple) assert c2.range == g.indexes_of(e, f, _type=tuple) assert c3.range == g.indexes_of(a, f, _type=tuple) assert g.outputs_of(b) == g.indexes_of(c) assert g.outputs_of(d) == g.indexes_of(e) assert g.outputs_of(f) == set()
def test_using_same_cursor_many_times_for_fork(): a, b, c, d, e = get_pseudo_nodes(5) g = Graph() c0 = g >> a >> b c0 >> c c0 >> d c0 >> e assert g.outputs_of(BEGIN) == g.indexes_of(a) assert g.outputs_of(a) == g.indexes_of(b) assert g.outputs_of(b) == g.indexes_of(c, d, e) assert g.outputs_of(c) == set() assert g.outputs_of(d) == set() assert g.outputs_of(e) == set()
def test_add_nodes_inbetween_branches(): a, b, c, d, e, f, x, y = get_pseudo_nodes(8) g = Graph() c0 = g.orphan() >> a >> b c1 = g.orphan() >> x >> y c2 = c0 >> c >> d >> c1 c3 = c0 >> e >> f >> c1 assert c0.range == g.indexes_of(a, b, _type=tuple) assert c1.range == g.indexes_of(x, y, _type=tuple) assert c2.range == g.indexes_of(a, y, _type=tuple) assert c3.range == g.indexes_of(a, y, _type=tuple) assert g.outputs_of(b) == g.indexes_of(c, e) assert g.outputs_of(d) == g.indexes_of(x) assert g.outputs_of(f) == g.indexes_of(x) assert g.outputs_of(y) == set()
def test_implicit_cursor_usage(): a, b, c = get_pseudo_nodes(*"abc") g = Graph() g >> a >> b >> c assert len(g) == 3 assert g.outputs_of(BEGIN) == {g.index_of(a)} assert g.outputs_of(a) == {g.index_of(b)} assert g.outputs_of(b) == {g.index_of(c)} assert g.outputs_of(c) == set()
def test_bonodoo_function_single(self): folder = tempfile.TemporaryDirectory() filename = 'test_file.csv' read = OdooModelFunction(model='res.users', function='test_function') value_1 = {'id': 2} with patch('xmlrpc.client.ServerProxy') as mk: mock_server = mk.return_value mock_server.login.return_value = 1 mock_server.execute_kw.return_value = value_1 graph = Graph() graph.add_chain(read, CsvWriter(filename, fs='fs.data')) bonobo.run(graph, services={ 'fs.data': bonobo.open_fs(folder.name), 'odoo.server': self.server, }) mk.assert_called() with open(os.path.join(folder.name, filename), 'r') as f: lines = f.readlines() self.assertEqual(len(lines), 1) self.assertEqual(ast.literal_eval(lines[0]), value_1) folder.cleanup()
def test_cursor_usage_to_add_a_chain_in_a_context_manager(): a, b, c = get_pseudo_nodes(*"abc") g = Graph() with g as cur: cur >> a >> b >> c assert len(g) == 3 assert g.outputs_of(BEGIN) == {g.index_of(a)} assert g.outputs_of(a) == {g.index_of(b)} assert g.outputs_of(b) == {g.index_of(c)} assert g.outputs_of(c) == set()
def test_graph_outputs_of(): g = Graph() # default graph only node assert len(g.outputs_of(BEGIN)) == 0 # unexisting node with pytest.raises(KeyError): g.outputs_of(0) # create node assert len(g.outputs_of(0, create=True)) == 0 assert len(g.outputs_of(0)) == 0
def test_graph_add_component(): g = Graph() assert len(g.nodes) == 0 g.add_node(identity) assert len(g.nodes) == 1 g.add_node(identity) assert len(g.nodes) == 2
def test_connect_two_anonymous_nodes(): g = Graph() a, b = get_pseudo_nodes(*"ab") # Create two "anonymous" nodes g.add_node(a) g.add_node(b) # Connect them g.add_chain(_input=a, _output=b)
def test_cursor_merge(): a, b, c = get_pseudo_nodes(*"abc") g = Graph() c1 = g >> a >> c c2 = g >> b >> c assert len(g) == 3 assert g.outputs_of(BEGIN) == g.indexes_of(a, b) assert g.outputs_of(a) == g.indexes_of(c) assert g.outputs_of(b) == g.indexes_of(c) assert g.outputs_of(c) == set() assert c1 == c2
def test_named_nodes(): g = Graph() a, b, c, d, e, f = get_pseudo_nodes(*"abcdef") # Here we mark _input to None, so normalize won't get the "begin" impulsion. g.add_chain(e, f, _input=None, _name="load") # Add two different chains g.add_chain(a, b, _output="load") g.add_chain(c, d, _output="load")
def test_graph_topological_sort(): g = Graph() a1, a2, a3, b1, b2 = get_pseudo_nodes("a1", "a2", "a3", "b1", "b2") g.add_chain(a1, a2, a3, _input=None, _output=None) assert g.topologically_sorted_indexes == (0, 1, 2) assert g[0] == a1 assert g[1] == a2 assert g[2] == a3 g.add_chain(b1, b2, _output=a2) assert g.topologically_sorted_indexes[-2:] == (1, 2) assert g.topologically_sorted_indexes.index( 3) < g.topologically_sorted_indexes.index(4) assert g[3] == b1 assert g[4] == b2
def test_cursor_merge_orphan_in_between(): a, b, c, v, w, x, y = get_pseudo_nodes(*"abcdefg") g = Graph() g >> a >> b >> c assert len(g) == 3 g.orphan() >> v >> w >> b assert len(g) == 5 g.orphan() >> x >> y >> b assert len(g) == 7 assert g.outputs_of(BEGIN) == g.indexes_of(a) assert g.outputs_of(a) == g.indexes_of(b) assert g.outputs_of(b) == g.indexes_of(c) assert g.outputs_of(c) == set() assert g.outputs_of(v) == g.indexes_of(w) assert g.outputs_of(w) == g.indexes_of(b) assert g.outputs_of(x) == g.indexes_of(y) assert g.outputs_of(y) == g.indexes_of(b)
def test_graph_index_of(): g = Graph() foo, bar, not_there = get_pseudo_nodes("foo", "bar", "not_there") g.add_node(foo) g.add_node(bar) # sequential, can resolve objects assert g.index_of(foo) == 0 assert g.index_of(bar) == 1 # calling on an index should return the index assert g.index_of(bar) == g.index_of(g.index_of(bar)) # not existing should raise value error with pytest.raises(ValueError): g.index_of(not_there) # tokens resolve to themselves assert g.index_of(BEGIN) == BEGIN
def test_concat_branches(): a, b, c, d = get_pseudo_nodes(4) g = Graph() c0 = g.orphan() >> a >> b c1 = g >> c >> d c2 = c1 >> c0 assert c0.first == g.index_of(a) assert c2.first == BEGIN assert c2.last == g.index_of(b) assert g.outputs_of(BEGIN) == g.indexes_of(c) assert g.outputs_of(a) == g.indexes_of(b) assert g.outputs_of(b) == set() assert g.outputs_of(c) == g.indexes_of(d) assert g.outputs_of(d) == g.indexes_of(a)
def test_add_more_branches_inbetween(): a, b, c, d, e, f, x, y = get_pseudo_nodes(8) g = Graph() c0 = g.orphan() >> a >> b c1 = g.orphan() >> c >> d c2 = g.orphan() >> e >> f c3 = g.orphan() >> x >> y c4 = c0 >> c1 >> c3 c5 = c0 >> c2 >> c3 assert c0.range == g.indexes_of(a, b, _type=tuple) assert c1.range == g.indexes_of(c, d, _type=tuple) assert c2.range == g.indexes_of(e, f, _type=tuple) assert c3.range == g.indexes_of(x, y, _type=tuple) assert c4.range == g.indexes_of(a, y, _type=tuple) assert c5.range == g.indexes_of(a, y, _type=tuple) assert g.outputs_of(b) == g.indexes_of(c, e) assert g.outputs_of(d) == g.indexes_of(x) assert g.outputs_of(f) == g.indexes_of(x) assert g.outputs_of(y) == set()
def test_cursor_to_fork_a_graph(): a, b, c, d, e = get_pseudo_nodes(*"abcde") g = Graph() g >> a >> b >> c g.get_cursor(b) >> d >> e assert len(g) == 5 assert g.outputs_of(BEGIN) == {g.index_of(a)} assert g.outputs_of(a) == {g.index_of(b)} assert g.outputs_of(b) == {g.index_of(c), g.index_of(d)} assert g.outputs_of(c) == set() assert g.outputs_of(d) == {g.index_of(e)} assert g.outputs_of(e) == set()
def test_cursor_to_fork_at_the_end(): a, b, c, d, e = get_pseudo_nodes(*"abcde") g = Graph() c0 = g >> a >> b c1 = c0 >> c c2 = c0 >> d >> e assert len(g) == 5 assert g.outputs_of(BEGIN) == {g.index_of(a)} assert g.outputs_of(a) == {g.index_of(b)} assert g.outputs_of(b) == {g.index_of(c), g.index_of(d)} assert g.outputs_of(c) == set() assert g.outputs_of(d) == {g.index_of(e)} assert g.outputs_of(e) == set() assert c0.first == g.index_of(BEGIN) assert c0.last == g.index_of(b) assert c1.first == g.index_of(BEGIN) assert c1.last == g.index_of(c) assert c2.first == g.index_of(BEGIN) assert c2.last == g.index_of(e)