Security implications of running untrusted JSON

115 views
Skip to first unread message

Aeneas Rekkas

unread,
May 5, 2020, 6:25:37 AM5/5/20
to Jsonnet
Since I could not find an answer in the documentation or on GitHub I thought the best place would be to ask here. Assuming that I create JSONNet snippets such as the following

local claims = std.extVar("claims");


{
  traits
: {
    username
: "Alice",
    website
: claims.website
 
}
}

and allow claims to be any valid JSON string that also is untrusted (e.g. coming from a third party) and load it like this (Go version)

vm := jsonnet.MakeVM()
vm.ExtCode("claims",`{ "website": "I AM UNTRUSTED", "foo": "CAN THIS PAYLOAD HACK SOMETHING?" }`)
o,err :=vm.EvaluateSnippet("my-file.jsonnet",`
local claims = std.extVar("claims");

{
  traits: {
    username: "Alice",
    website: claims.website
  }
}`)

is there anything I need to know in terms of security? Can this be abused in any way (e.g. writing files, causing tons of CPU or memory cycles) and if so how can I prevent that? The only other way I have found is to use `vm.ExtVar` which only allows me to set strings though.

Thank you!

Aeneas Rekkas

unread,
May 5, 2020, 6:39:30 AM5/5/20
to Jsonnet
For clarification, the claims payload is coming frmo a JSON Decoder:

var b bytes.Buffer
json
.NewEncoder(b).Encode(map[string]interface{}{"website": "I AM UNTRUSTED", "foo": "CAN THIS PAYLOAD HACK SOMETHING?"})
vm.ExtCode("claims", b.String())

Dave Cunningham

unread,
May 5, 2020, 8:00:47 AM5/5/20
to Aeneas Rekkas, Jsonnet
As long as you are sure that the string passed to vm.ExtCode is just JSON and not arbitrary Jsonnet then it can have no side effects such as reading files etc.  Just make sure you can parse the JSON string with a standard JSON parser before giving it to vm.ExtCode. Then the JSON is not really "run" because it's just a constant Jsonnet value.

Beyond that, it's like with other programming languages.

The size of the input could be an issue. What happens if someone gives you a gig of JSON?  It would be prudent to put a bytes limit on it.

Then it's up to whatever the rest of your code does -- does it have safe behaviour for arbitrary input?  Or will it go into an infinite loop if some input parameter is less than 0 or whatever.  Make sure you validate the input if you can't handle arbitrary inputs.


--
You received this message because you are subscribed to the Google Groups "Jsonnet" group.
To unsubscribe from this group and stop receiving emails from it, send an email to jsonnet+u...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/jsonnet/37b33f6e-a3a2-49ca-a8ce-c7cfd2ce1d3d%40googlegroups.com.

Aeneas Rekkas

unread,
May 5, 2020, 8:07:09 AM5/5/20
to Dave Cunningham, Jsonnet
Thank you for taking the time to answer my question. It is exactly what I was looking for both in terms of clarity and outcome!
Reply all
Reply to author
Forward
0 new messages