How to use SecureJsonData and OAuth in a panel plugin

I’m fairly new to Grafana plugin development, so I’m just looking for some guidance here.

My end goal is to create a panel with a button on it. When the button is pressed, a REST call will be made that is proxied through the Grafana server where an API key can be added to the request. It looks like this is only possible with a data source, but I’d like to do this with just a panel.

That’s not completely it, though. I’d also like a way to add the username of the person making the request to the REST call. The point of this would be so that the program that handles the REST call would see there’s a valid API key, but could then decide if the user has permission to execute the given request. This is especially important because I do not want to allow users that are not logged in to be able to make this request. It’s important that this data isn’t added in the front end, as it could easily be spoofed.

Ideally I wouldn’t have to make a data source plugin at all for what I’m trying to accomplish, but it doesn’t look like I get the same features as a data source if I’m just trying to make a panel.

My fallback option would be to make this dashboard private and just have the API key passed to the front end, but I’d like to avoid making the dashboard private.

It sounds like you’re already aware of this, but I’ll clarify this for anyone Googling their way here:

Since panel options are stored unencrypted, I highly advise against making authenticated requests from a panel plugin.

The only way to encrypt secrets is through a data source plugin. That being said, we’re aware that there are reasonable use cases for why you’d want to make a authenticated request for visualization purposes. For example, to fetch raster data from a commercial API for a map panel.

Unfortunately, there’s really no good way to do this other than through a data source. You could also set up a separate proxy that handles authentication and makes the endpoint publicly available to your Grafana instance.

Out of curiosity, and so that I can forward your feedback, could you explain a bit more about your use case?

Sure. I created a REST endpoint that, when hit with a certain payload, will turn on or off a generator. Ideally, I could have a public dashboard where any user (including anonymous users), can view the dashboard, and even click the buttons that send out REST calls. Then, whatever receives the REST call can see which user sent it and decide if they are allowed to command the generator to turn on or off.

One thing I could do is have the panel plugin send the name of the user off to the REST endpoint along with an API key, however, the first problem is that the API key is being sent to the frontend, and the second problem is that any attacker could do the REST call themselves with a different user inside the payload.

My currently (not ideal) solution for this is to have a private dashboard that only certain logged in users can access. The API key still ends up being sent to the frontend, but at this point I’m not worried about people I trust using the API key maliciously.

1 Like