The issue pertains to api.zoom.us/v2/users/__USERID__/token)
Description
So I presently have the ZoomMtg.join working great, but in our situation we need a separate area where people with the Host role are able to connect. This is a zoom account (business I think) that has one account associated that is used by teachers. So really we just want to be able to get the ZAK for that account, and then allow them to start the meeting.
The issue that I am having is what exactly is YOUR_SECRET_TOKEN. Each of the situations that I tried (see below) keep returning Invalid access token. As I mentioned before, I can connect just fine to the meeting as a participant so it’s not the keys I don’t think.
Sorry your response is somewhat vague. I already setup the General App so that’s fine and working when joining meetings.
Is it the Client Secret token provided that matches to the Client ID? Or is there some other format that needs to be provided? Also does it need to be encrypted?
What I already tried (as mentioned above) is a few different solutions but none of them seem to work.
Just the secret token
Pay load (see above Signature comprised of comment)
Hey!
You have to generate an access token after authorizing your General app.
Once you authorize the app, you will receive an authorization code in your URL, you will grab that one to make a call to our OAuth endpoint to get an access token.
Here is a blog that might be helpful
Here is a sample app that might help you as a guide too:
So are you indicating that I need to setup an oAuth? Also does that need to be publlished? I took a look at the Postman post but it’s not really related to my scenario. I’m ok in terms of having created a connection it’s just the SECRET TOKEN I’m really having an issue with.
What I did realize is that the Secret Token is not the Client Secret.
So in my General App I have a SECRET_TOKEN but when I tried with curl I still get Invalid Token. Then I tried it with a Server-to-Server oAuth app that I have and that also didn’t work (same message).
So my questions are:
I am going to assume that we use a Server-toServer oAuth because you can’t really create an oAuth app. Is that correct?
Does it need to be published or can I leave it in dev mode?
Do I need to have an oAuth or can I use a General App
When we attempt to access /users/{user_id}/token is it correct to use the email address as the user_id?
Also, so we are on the same page this would be the correct secret token right? (Sorry I tried to upload an image but I am not allowed). In an App(s)
General App : Features> Access
Server-to-Server App: Feature
It indicates
These features allow you to access Zoom data via APIs and Event Subscriptions. You can also allow your app to access Zoom’s APIs and receive real-time updates on events.
I don’t really want to use Postman honestly. I would rather keep this simple and happy to test with CURL. I just need to figure out why the secret token is not working. Is there any way you are able to check my account perhaps?
Also I feel like we are confusing the concept of oAuth access token and ZAK. I only want the ZAK token not an oAuth, which what I understand is that I don’t need the oAuth but I could be wrong.
Hi @shaneonabike
Thanks for getting back to me and I understand if you dont want to use Postman, Curl is totally fine!
I see where the confusion can be, the secret token that you can see in your General App: Features > Access or Server to Server App: Feature, is not to be used to make API requests, that Secret token is used to verify event notifications sent by Zoom (webhooks)
I do not know where you got that code snippet from but I want to agree with you that the fact that the token is called “Your_secret_token” can be very misleading, it should be called “access_token”, which is the token that you should be generating using either a Server to Server OAuth app or a General app and that token should be generated using your client ID and client Secret.
If you are developing an internal application and your goal is to keep it private, you can stick with the Server to Server Oauth app.
So the curl command to generate an access token using your Server to server oauth app would look like this:
For good measure I compared the base64 that was generated and it matches, as well as the Account ID and Client ID/Secret. The only (gutt feeling) issue I have is that my Account ID has a dash in it. I’m worried somehow that is messed up?
I found the problem. It would appear as though http_build_query actually adds a hidden new line in the output (or something else) that is tripping up your end. I had to build the post elements by hand in PHP and it’s working.
I am having issues now with teh signature needed to connect to a meeting though.
For anyone else that comes across this I just wanted to summarize what was discovered and how to get it to work, but it’s not entirely clear.
Server-to-Server app is used to obtain tokens/Zaks
General App is used to connect to the API
Connecting as a host
Obtain a access access code via a Server-to-Server App
Generate a Zak token for a specific Zoom account attached to your account
Generate a signature to access the API
Notes
For the access token and zak token you need the Account ID, Client ID/Secret for the Server-to-Server AND the email account for the user who is connecting as a host (that is on the Zoom account you are connecting too)
http_build_query didn’t work for me on PHP 8.x in the case with Zoom. When I built the post data myself it was fine, but not with that call no idea why.
My curl call function isn’t anything special, but you have to remember that if there is postData then the header needs to be Authorization: Basic $accessToken, otherwise it should be Authorization: Bearer $accessToken
// Obtain Initial access
$dataRetrieved = [];
$postData = [
'grant_type' => 'account_credentials',
'account_id' => $accountId,
];
$token = '';
$accessToken = base64_encode($clientId . ':' . $clientSecret);
$url = 'https://zoom.us/oauth/token';
$error = zoompage_make_curlCall($url, $accessToken, $dataRetrieved, $postData);
// We found an error we need to return it
if (!empty($error)) {
return $error;
}
else {
//echo "<br>Found ".var_export($dataRetrieved,true);
// Process access token
if (isset($dataRetrieved['access_token'])) {
$token = $dataRetrieved['access_token'];
}
else {
error_log("Could not properly complete {$url}: Received message " . var_export($dataRetrieved,true));
return ['error' => 'No Access Token'];
}
}
//echo '<br>Token found '.var_export($token,true);
// Obtain Zak
$dataRetrieved = [];
$postData = [];
$url = "https://api.zoom.us/v2/users/{$accountEmail}/token?type=zak&ttl=7776000";
$error = zoompage_make_curlCall($url, $token, $dataRetrieved, $postData);
$zakToken = '';
// We found an error we need to return it
if (!empty($error)) {
return $error;
}
else {
if (isset($dataRetrieved['token'])) {
$zakToken = $dataRetrieved['token'];
}
else {
error_log("Could not properly complete {$url}: Received message " . var_export($dataRetrieved,true));
return ['error' => 'No Access Token'];
}
}
return $zakToken;