Repository: onflow/flow-cli (go)

Issue:
Cannot supply boolean as initialization argument for contract
### Problem
Cannot supply boolean value as initialization argument for contract via flow-cli

### Steps to Reproduce

Create a contract that takes a boolean value argument into its constructor (init function), and put that arg into a `flow.json` as either a string value "true" or "false", or a naked bool value true or false. The cli will throw an error either way.

### Acceptance Criteria

n/a

### Context

nothing of consequence, and numerous workarounds are available.

### example
```
    "deployments": {
    "emulator": {
      "one": [{
          "name": "Emit",
          "args": [
            {"type": "String", "value": "test"},
            {"type": "Bool", "value": true}
          ]
```
results in: 

```
❯ flow emulator --persist -v
json: cannot unmarshal bool into Go struct field jsonConfig.deployments of type string
```

and:
```
    "deployments": {
    "emulator": {
      "one": [{
          "name": "Emit",
          "args": [
            {"type": "String", "value": "test"},
            {"type": "Bool", "value": "true"}
          ]
```

results in:

```
❯ flow emulator --persist -v
failed to decode value: invalid JSON Cadence structure
```


Pull request:
FIx for parsing boolean types in the configuration
Closes #351 

## Description

* changed the args of the deployment type to `map[string]interface{}` to emulate a generic, so one can supply values of other types than solely `string`.
* added a switch to check the `cadence..ID()` for `Bool`, to handle the boolean case. the only other match in the switch is default, to maintain consistency with the former behavior of the parser.
* added appropriate tests in the go test file. 
* manual testing that boolean was accepted into contract constructor is outlined below

manual testing:
`flow.json`
```
...
    "contracts": {
    "Emit": "/home/drifter/code/dapps/3mittr-backend/emitContract.cdc",
    "Test": "/home/drifter/code/dapps/3mittr-backend/testContract.cdc"
  },
    "deployments": {
    "emulator": {
      "one": [
        {
          "name": "Test",
          "args": [
            {"type": "String", "value": "test"},
            {"type": "Bool", "value": true} <- TEST CASE
          ]}
      ]
    }
  }

```

`testContract.cdc`
```
pub contract Test {
    pub let message: String
    pub let someBool: Bool

    init(message: String, someBool: Bool) {
        self.message = message
        self.someBool = someBool

        log(self.message)
        log(self.someBool)
    }
}
```

`deployment & emulator output`:
```
❯ ~/code/flow-cli/cmd/flow/flow-x86_64-linux- -f ~/flow.json project deploy --network emulator

Deploying 1 contracts for accounts: one

Test -> 0xf8d6e0586b0a20c7 (923f8863f31779872f7e18890fdb678c76bde9a83e414b6c177357234e120b55)


✨ All contracts deployed successfully

```
**NOTE** the binary listed above was build after code update with the Makefile in the project.
```
INFO[0093] ⭐  Transaction executed                       txID=923f8863f31779872f7e18890fdb678c76bde9a83e414b6c177357234e120b55
DEBU[0093] LOG [923f88] "test"
DEBU[0093] LOG [923f88] true
DEBU[0093] EVT [923f88] flow.AccountContractAdded: 0x5a350ae7ec8a40b5543ed45459929f56d11c8e2a30c224ceba6c8887b162c9ac
DEBU[0093] 📦  Block #1 committed                         blockHeight=1 blockID=6060b40802c685736fcf209c69cb518e26509f1be31e224bbfa0d9b54f2d0569
DEBU[0093] 📝  GetTransactionResult called                txID=923f8863f31779872f7e18890fdb678c76bde9a83e414b6c177357234e120b55
```
______

For contributor use:

- [x] Targeted PR against `master` branch
- [x] Linked to Github issue with discussion and accepted design OR link to spec that describes this work
- [x] Code follows the [standards mentioned here](https://github.com/onflow/flow-cli/blob/master/CONTRIBUTING.md#styleguides)
- [x] Updated relevant documentation (N/A
- [x] Re-reviewed `Files changed` in the Github PR explorer
- [x] Added appropriate labels


Patch:
diff --git a/pkg/flowkit/config/json/deploy.go b/pkg/flowkit/config/json/deploy.go
index 5e156eab..fdc6a12b 100644
--- a/pkg/flowkit/config/json/deploy.go
+++ b/pkg/flowkit/config/json/deploy.go
@@ -101,12 +101,20 @@ func transformDeploymentsToJSON(configDeployments config.Deployments) jsonDeploy
 					simple: c.Name,
 				})
 			} else {
-				args := make([]map[string]string, 0)
+				args := make([]map[string]interface{}, 0)
 				for _, arg := range c.Args {
-					args = append(args, map[string]string{
-						"type":  arg.Type().ID(),
-						"value": fmt.Sprintf("%v", arg.ToGoValue()),
-					})
+					switch arg.Type().ID() {
+					case "Bool":
+						args = append(args, map[string]interface{}{
+							"type":  arg.Type().ID(),
+							"value": arg.ToGoValue(),
+						})
+					default:
+						args = append(args, map[string]interface{}{
+							"type":  arg.Type().ID(),
+							"value": fmt.Sprintf("%v", arg.ToGoValue()),
+						})
+					}
 				}
 
 				deployments = append(deployments, deployment{
@@ -132,8 +140,8 @@ func transformDeploymentsToJSON(configDeployments config.Deployments) jsonDeploy
 }
 
 type contractDeployment struct {
-	Name string              `json:"name"`
-	Args []map[string]string `json:"args"`
+	Name string                   `json:"name"`
+	Args []map[string]interface{} `json:"args"`
 }
 
 type deployment struct {


Test patch:
diff --git a/pkg/flowkit/config/json/deploy_test.go b/pkg/flowkit/config/json/deploy_test.go
index cb346fb1..fd2a53d3 100644
--- a/pkg/flowkit/config/json/deploy_test.go
+++ b/pkg/flowkit/config/json/deploy_test.go
@@ -124,7 +124,8 @@ func Test_DeploymentAdvanced(t *testing.T) {
 					"name": "Kibble",
 					"args": [
 						{ "type": "String", "value": "Hello World" },
-						{ "type": "Int8", "value": "10" }
+						{ "type": "Int8", "value": "10" },
+						{ "type": "Bool", "value": false }
 					]
 				},
 				"KittyItemsMarket"
@@ -143,9 +144,11 @@ func Test_DeploymentAdvanced(t *testing.T) {
 	assert.Len(t, alice, 1)
 	assert.Len(t, alice[0].Contracts, 2)
 	assert.Equal(t, alice[0].Contracts[0].Name, "Kibble")
-	assert.Len(t, alice[0].Contracts[0].Args, 2)
+	assert.Len(t, alice[0].Contracts[0].Args, 3)
 	assert.Equal(t, alice[0].Contracts[0].Args[0].String(), `"Hello World"`)
 	assert.Equal(t, alice[0].Contracts[0].Args[1].String(), "10")
+	assert.Equal(t, alice[0].Contracts[0].Args[2].Type().ID(), "Bool")
+	assert.False(t, alice[0].Contracts[0].Args[2].ToGoValue().(bool))
 	assert.Equal(t, alice[0].Contracts[1].Name, "KittyItemsMarket")
 	assert.Len(t, alice[0].Contracts[1].Args, 0)
 }