Also, as my users have to access the data anyway I will need to have a public key for the outside world somewhere in between.
Exactly. Take the stateless HTTP, who would otherwise not know what resource it should request: it exposes your question's ID 218306
in the URL. Perhaps you're actually wondering whether an exposed identifier may be predictable?
The only places where I've heard a negative answer to that, used the rationale: "But they can change the ID in the URL!". So they used GUIDs instead of implementing proper authorization.
I can imagine one situation where you don't want your identifiers to be predictable: resource harvesting. If you have an site that publicly hosts certain resources others may be interesting in, and you host them like /images/n.jpg
or /videos/n.mp4
where n
just is an incrementing number, anyone looking at traffic to and from your website can harvest all your resources.
So, to directly answer your question: no, it is not bad to directly "expose" identifiers that only have meaning to your program, usually it is even required for your program to succesfully operate.
There is no 100% secure solution. What ever you implement must be executable by a deterministic computer, so someone and substitute that and unpick what ever technical barriers you put in their way. You can make it more technically challenging and a more involved and slower process, but in time if the incentives are there, someone will break it.
If you are implementing this in .NET then, by default it is trivial for someone to obtain C# style source code to your application, and then to step through their C# code in a debugger. It is a little more complex in C/C++, but again not impossible. I do not know how much of a challenge this is with JAVA, but I would not expect it to be a significant hurdle.
There are processes that can be applied to make the code harder for a human to read, but do very little to make it harder for a computer to single step through the code. Someone can put a breakpoint in the system library and then back track up the call stack to see if this call to a network socket is of interest without having to understand your code base.
I have also seen encryption techniques used, where a program decrypts the actual code during run time. However, again, a determined hacker can just run this part of the code, obtain the decrypted code and then reverse engineer this into source code.
The best solution is to assume it will become compromised, and then ensure that the process for changing the sensitive data is trivial for you, and to process to compromise the sensitive data is as hard as possible for everyone else. That's why some systems require a web call to obtain the data. You can then block calls from IP's or from client certificates that you no longer trust, and give everyone else 'this months' application key.
In the end, you need to consider the consequences for having the data publicly known, and then decide how far you need to go, to make the process for obtaining it more skilled and and more time consuming.
Best Answer
It depends on what the API key does. However, if the API key is giving you access to something or controlling your access to something, why would you want other people to piggyback on the resources that you have access to? You wouldn't.
Think about it this way. I own a service and you are a user of it, perhaps even a paying customer. I give you an API key based on an agreed upon level of service (perhaps API calls per unit of time). If this API key was public, other people could use it to pretend to be you and use up your limited API calls.
That's probably the least concerning situation. Sharing of API keys becomes more of a concern if the API key authenticates someone for access to a subset of data.
The methods of protecting API keys depends on the technology that you are using. When developing web or mobile applications, for example, you can help protect your API keys by ensuring they don't end up on the client (the web browser or the mobile device). Instead, they can remain on the servers used by the client. The client can authenticate against the services which can then make appropriate calls. Depending on the environment, the API keys can even be encrypted as they are stored in different environments.