From 1b75ace7ba4983efef2ee9d92da7440005e37912 Mon Sep 17 00:00:00 2001 From: tenmoves Date: Mon, 2 Jan 2023 18:49:02 +0100 Subject: [PATCH] Use Interpreter parsing to check the prior code --- .../contracts/interpreter/condition.ex | 23 ++++++++++ .../contracts/interpreter/condition_test.exs | 46 +++++++++++++++++++ 2 files changed, 69 insertions(+) diff --git a/lib/archethic/contracts/interpreter/condition.ex b/lib/archethic/contracts/interpreter/condition.ex index 14c887c45..5b97fa891 100644 --- a/lib/archethic/contracts/interpreter/condition.ex +++ b/lib/archethic/contracts/interpreter/condition.ex @@ -560,6 +560,21 @@ defmodule Archethic.Contracts.ConditionInterpreter do {"content", true} end + defp validate_condition({"code", nil}, %{ + "next" => %{"code" => next_code}, + "previous" => %{"code" => prev_code} + }) do + quoted_next_code = + next_code + |> Code.string_to_quoted!(static_atoms_encoder: &atom_encoder/2) + + quoted_previous_code = + prev_code + |> Code.string_to_quoted!(static_atoms_encoder: &atom_encoder/2) + + {"code", quoted_next_code == quoted_previous_code} + end + # Validation rules for inherit constraints defp validate_condition({field, nil}, %{"previous" => prev, "next" => next}) do {field, Map.get(prev, field) == Map.get(next, field)} @@ -598,4 +613,12 @@ defmodule Archethic.Contracts.ConditionInterpreter do {res, _} = Code.eval_quoted(quoted_code, scope: constants) res end + + defp atom_encoder(atom, _) do + if atom in ["if"] do + {:ok, String.to_atom(atom)} + else + {:ok, {:atom, atom}} + end + end end diff --git a/test/archethic/contracts/interpreter/condition_test.exs b/test/archethic/contracts/interpreter/condition_test.exs index f54c4d540..dec111163 100644 --- a/test/archethic/contracts/interpreter/condition_test.exs +++ b/test/archethic/contracts/interpreter/condition_test.exs @@ -276,5 +276,51 @@ defmodule Archethic.Contracts.ConditionInterpreterTest do } }) end + + test "should return true if the ast of the code is the same" do + assert ~s""" + condition inherit: [] + """ + |> Interpreter.sanitize_code() + |> elem(1) + |> ConditionInterpreter.parse() + |> elem(2) + |> ConditionInterpreter.valid_conditions?(%{ + "previous" => %{ + "code" => ~s""" + condition inherit: [ ] + """ + }, + "next" => %{ + "code" => ~s""" + condition inherit: [] + + + """ + } + }) + end + + test "should return false if the ast of the code is the different" do + refute ~s""" + condition inherit: [] + """ + |> Interpreter.sanitize_code() + |> elem(1) + |> ConditionInterpreter.parse() + |> elem(2) + |> ConditionInterpreter.valid_conditions?(%{ + "previous" => %{ + "code" => ~s""" + condition inherit: [ ] + """ + }, + "next" => %{ + "code" => ~s""" + condition inherit: [1] + """ + } + }) + end end end