zoho token management

This commit is contained in:
Ralph Soika 2025-04-25 09:52:50 +02:00
parent c47a6ed4ac
commit 39099700fe
3 changed files with 162 additions and 68 deletions

View file

@ -71,4 +71,18 @@ public class ZohoController extends ConfigController {
this.getWorkitem().setItemValue("message", message); this.getWorkitem().setItemValue("message", message);
} }
} }
/**
* Ruft zohoOAuhtManager.refreshToken auf
*/
public void refreshAccessToken() {
//
try {
zohoOAuthManager.refreshAccessToken();
} catch (PluginException e) {
String message = "Failed to refresh token: " + e.getMessage();
logger.warning(message);
this.getWorkitem().setItemValue("message", message);
}
}
} }

View file

@ -8,6 +8,7 @@ import java.net.http.HttpRequest;
import java.net.http.HttpResponse; import java.net.http.HttpResponse;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.time.Duration; import java.time.Duration;
import java.util.Date;
import java.util.logging.Logger; import java.util.logging.Logger;
import org.imixs.workflow.ItemCollection; import org.imixs.workflow.ItemCollection;
@ -56,6 +57,11 @@ public class ZohoOAuthManager {
this.jsonb = JsonbBuilder.create(); this.jsonb = JsonbBuilder.create();
} }
@Lock(LockType.READ)
public String getValidAccessToken() {
return accessToken;
}
/** /**
* Step 3: Generate Access and Refresh Token * Step 3: Generate Access and Refresh Token
* *
@ -112,19 +118,8 @@ public class ZohoOAuthManager {
TokenResponse tokenResponse = jsonb.fromJson(response.body(), TokenResponse tokenResponse = jsonb.fromJson(response.body(),
TokenResponse.class); TokenResponse.class);
saveTokenData(zohoConfig, tokenResponse);
accessToken = tokenResponse.getAccess_token();
logger.info("│ ├── accessToken=" + accessToken);
refreshToken = tokenResponse.getRefresh_token();
logger.info("│ ├── refreshToken=" + refreshToken);
logger.info("│ ├── expires_in=" + tokenResponse.getExpires_in());
zohoConfig.setItemValue("zoho.accessToken", accessToken);
zohoConfig.setItemValue("zoho.refreshToken", refreshToken);
zohoConfig.setItemValue("zoho.expires", tokenResponse.getExpires_in());
zohoConfig.setItemValue("message", "Access Token OK");
configService.save(zohoConfig);
} else { } else {
throw new RuntimeException("Failed to get tokens: " + throw new RuntimeException("Failed to get tokens: " +
response.statusCode() + " - " + response.body()); response.statusCode() + " - " + response.body());
@ -136,65 +131,111 @@ public class ZohoOAuthManager {
} }
} }
@Lock(LockType.READ)
public String getValidAccessToken() {
return null;
}
/** /**
* This method updates the Access Token based on the current Refresh Token * This method updates the Access Token based on the current Refresh Token
* *
* @throws IOException * @throws IOException
* @throws PluginException
*/ */
public void testRefreshAccessToken() throws IOException { @Lock(LockType.WRITE)
public void refreshAccessToken() throws PluginException {
// logger.info("├── refresh Zoho access token"); logger.info("├── refresh Zoho access token");
// refreshToken =
// "1000.cf458816e97f848df8134ce1c7e923a1.5b9dbdee317e35d7f0c619e7648d55ff";
// try {
// String requestUrl = "https://accounts.zoho.eu/oauth/v2/token" + ItemCollection zohoConfig = configService.loadConfiguration(ZohoController.ZOHO_CONFIGURATION);
// "?refresh_token=" + URLEncoder.encode(refreshToken, StandardCharsets.UTF_8) +
// "&client_id=" + URLEncoder.encode(clientID.get(), StandardCharsets.UTF_8) +
// "&client_secret=" + URLEncoder.encode(clientSecret.get(),
// StandardCharsets.UTF_8) +
// "&grant_type=refresh_token";
// logger.info("│ ├── Request URI=" + requestUrl); String clientID = zohoConfig.getItemValueString("zoho.clientid");
String clientSecret = zohoConfig.getItemValueString("zoho.clientsecret");
// HttpRequest request = HttpRequest.newBuilder() refreshToken = zohoConfig.getItemValueString("zoho.refreshToken");
// .uri(URI.create(requestUrl)) try {
// .header("Content-Type", "application/x-www-form-urlencoded")
// .POST(HttpRequest.BodyPublishers.noBody()) // Wichtig: Kein Body!
// .build();
// HttpResponse<String> response; String requestUrl = "https://accounts.zoho.eu/oauth/v2/token" +
"?refresh_token=" + URLEncoder.encode(refreshToken, StandardCharsets.UTF_8) +
"&client_id=" + URLEncoder.encode(clientID, StandardCharsets.UTF_8) +
"&client_secret=" + URLEncoder.encode(clientSecret,
StandardCharsets.UTF_8)
+
"&grant_type=refresh_token";
// response = httpClient.send(request, logger.info("│ ├── Request URI=" + requestUrl);
// HttpResponse.BodyHandlers.ofString());
// logger.info("│ ├── Response statusCode=" + response.statusCode()); HttpRequest request = HttpRequest.newBuilder()
// if (response.statusCode() == 200) { .uri(URI.create(requestUrl))
.header("Content-Type", "application/x-www-form-urlencoded")
.POST(HttpRequest.BodyPublishers.noBody()) // Wichtig: Kein Body!
.build();
// // 1. Response-Logging für Debugging HttpResponse<String> response;
// logger.info("│ ├── Response Body=" + response.body());
// TokenResponse tokenResponse = jsonb.fromJson(response.body(), response = httpClient.send(request,
// TokenResponse.class); HttpResponse.BodyHandlers.ofString());
// String accessToken = tokenResponse.getAccess_token(); logger.info("│ ├── Response statusCode=" + response.statusCode());
// logger.info("│ ├── accessToken=" + accessToken); if (response.statusCode() == 200) {
// logger.info("│ ├── expires_in=" + tokenResponse.getExpires_in());
// } else {
// throw new RuntimeException("Failed to get tokens: " +
// response.statusCode() + " - " + response.body());
// }
// } catch (IOException | InterruptedException e) { // 1. Response-Logging für Debugging
// throw new InvalidAccessException("Unable to resolve access tokens: " + logger.info("│ ├── Response Body=" + response.body());
// e.getMessage());
// } TokenResponse tokenResponse = jsonb.fromJson(response.body(),
TokenResponse.class);
saveTokenData(zohoConfig, tokenResponse);
// String accessToken = tokenResponse.getAccess_token();
// logger.info("│ ├── accessToken=" + accessToken);
// logger.info("│ ├── expires_in=" + tokenResponse.getExpires_in());
} else {
throw new RuntimeException("Failed to get tokens: " +
response.statusCode() + " - " + response.body());
}
} catch (IOException | InterruptedException e) {
throw new PluginException(ZohoOAuthManager.class.getSimpleName(),
ZohoOAuthManager.ERROR_CONFIG, "Unable to refresh access tokens: " + e.getMessage());
}
} }
/**
* Helper method to update the config itemcolleciton based on a tokenResponse
*
* @param zohoConfig
* @param tokenResponse
*/
private void saveTokenData(ItemCollection zohoConfig, TokenResponse tokenResponse) {
String apiDomain = tokenResponse.getApi_domain();
if (apiDomain != null && !apiDomain.isEmpty()) {
logger.info("│ ├── apiDomain=" + apiDomain);
zohoConfig.setItemValue("zoho.apiDomain", apiDomain);
}
String scope = tokenResponse.getScope();
if (scope != null && !scope.isEmpty()) {
logger.info("│ ├── scope=" + scope);
zohoConfig.setItemValue("zoho.scope", scope);
}
accessToken = tokenResponse.getAccess_token();
if (accessToken != null && !accessToken.isEmpty()) {
logger.info("│ ├── accessToken=" + accessToken);
zohoConfig.setItemValue("zoho.accessToken", accessToken);
}
refreshToken = tokenResponse.getRefresh_token();
if (refreshToken != null && !refreshToken.isEmpty()) {
logger.info("│ ├── refreshToken=" + refreshToken);
zohoConfig.setItemValue("zoho.refreshToken", refreshToken);
}
logger.info("│ ├── expires_in=" + tokenResponse.getExpires_in());
// Expires-Zeit in Millisekunden berechnen
long expiresInSeconds = tokenResponse.getExpires_in() - 60;
long currentTimeMillis = System.currentTimeMillis();
long expiresTimeMillis = currentTimeMillis + (expiresInSeconds * 1000);
// Expires-Zeit in ein Date-Objekt konvertieren
Date expiresDate = new Date(expiresTimeMillis);
zohoConfig.setItemValue("zoho.expires", expiresDate);
zohoConfig.setItemValue("message", "Access Token OK");
configService.save(zohoConfig);
}
} }

View file

@ -81,7 +81,6 @@
<p> <p>
<span class="typcn typcn-lightbulb"></span> Fordern Sie einen ZOHO API COde <span class="typcn typcn-lightbulb"></span> Fordern Sie einen ZOHO API COde
an an
<ol> <ol>
<li>Melden Sie sich auf der <a href="https://api-console.zoho.eu/" <li>Melden Sie sich auf der <a href="https://api-console.zoho.eu/"
target="_blank">ZOHO API Console</a> an</li> target="_blank">ZOHO API Console</a> an</li>
@ -94,8 +93,8 @@
<li> <li>
Generieren Sie einen neuen Access Code Generieren Sie einen neuen Access Code
<br /> <br />
Scope:<br /> Scope:
ZohoBooks.invoices.CREATE,ZohoBooks.invoices.READ,ZohoBooks.invoices.UPDATE,ZohoBooks.invoices.DELETE <code>ZohoBooks.invoices.CREATE,ZohoBooks.invoices.READ,ZohoBooks.invoices.UPDATE</code>
</li> </li>
<li> <li>
Code über den Button "Create" anfordern und in das Feld "Access Code" Code über den Button "Create" anfordern und in das Feld "Access Code"
@ -107,20 +106,60 @@
</li> </li>
</ol> </ol>
<h:commandButton actionListener="#{zohoController.updateAccessToken()}" <h:commandButton actionListener="#{zohoController.updateAccessToken()}"
value="Access Token Generieren"> value="Token generieren">
</h:commandButton>
<h:commandButton actionListener="#{zohoController.refreshAccessToken()}"
value="Refresh Access Token">
</h:commandButton> </h:commandButton>
<br />
<h:outputText value="#{zohoController.workitem.item['message']}" />
<br />
AccessToken:
<h:outputText value="#{zohoController.workitem.item['zoho.accesstoken']}" />
<br />
RefreshToken:
<h:outputText value="#{zohoController.workitem.item['zoho.refreshtoken']}" />
</p> </p>
</div>
<div class="imixs-form-section-2">
<h3>Status:
<h:outputText value="#{zohoController.workitem.item['message']}" />
</h3>
<table>
<tr>
<td><strong>API Domain: </strong></td>
<td>
<h:outputText
value="#{zohoController.workitem.item['zoho.apiDomain']}" />
</td>
</tr>
<tr>
<td><strong>Scope: </strong></td>
<td>
<h:outputText
value="#{zohoController.workitem.item['zoho.scope']}" />
</td>
</tr>
<tr>
<td><strong>AccessToken: </strong></td>
<td>
<h:outputText
value="#{!empty zohoController.workitem.item['zoho.accesstoken']?'OK':'NOK'}" />
</td>
</tr>
<tr>
<td>
<strong>RefreshToken: </strong>
</td>
<td>
<h:outputText
value="#{!empty zohoController.workitem.item['zoho.refreshtoken']?'OK':'NOK'}" />
</td>
</tr>
<tr>
<td>
<strong>Expires: </strong>
</td>
<td>
<h:outputText
value="#{zohoController.workitem.item['zoho.expires']}" />
</td>
</tr>
</table>
</div> </div>
</div> </div>