use of org.eclipse.che.api.factory.server.scm.exception.ScmConfigurationPersistenceException in project che-server by eclipse-che.
the class KubernetesGitCredentialManager method createOrReplace.
@Override
public void createOrReplace(PersonalAccessToken personalAccessToken) throws UnsatisfiedScmPreconditionException, ScmConfigurationPersistenceException {
try {
final String namespace = getFirstNamespace();
final KubernetesClient client = clientFactory.create();
// to avoid duplicating secrets we try to reuse existing one by matching
// hostname/username if possible, and update it. Otherwise, create new one.
Optional<Secret> existing = client.secrets().inNamespace(namespace).withLabels(SEARCH_LABELS).list().getItems().stream().filter(s -> s.getMetadata().getAnnotations() != null).filter(s -> Boolean.parseBoolean(s.getMetadata().getAnnotations().get(ANNOTATION_GIT_CREDENTIALS)) && personalAccessToken.getScmProviderUrl().equals(StringUtils.trimEnd(s.getMetadata().getAnnotations().get(ANNOTATION_SCM_URL), '/')) && personalAccessToken.getCheUserId().equals(s.getMetadata().getAnnotations().get(ANNOTATION_CHE_USERID)) && personalAccessToken.getScmUserName().equals(s.getMetadata().getAnnotations().get(ANNOTATION_SCM_USERNAME))).findFirst();
Secret secret = existing.orElseGet(() -> {
Map<String, String> annotations = new HashMap<>(DEFAULT_SECRET_ANNOTATIONS);
annotations.put(ANNOTATION_SCM_URL, personalAccessToken.getScmProviderUrl());
annotations.put(ANNOTATION_SCM_USERNAME, personalAccessToken.getScmUserName());
annotations.put(ANNOTATION_CHE_USERID, personalAccessToken.getCheUserId());
ObjectMeta meta = new ObjectMetaBuilder().withName(NameGenerator.generate(NAME_PATTERN, 5)).withAnnotations(annotations).withLabels(NEW_SECRET_LABELS).build();
return new SecretBuilder().withMetadata(meta).build();
});
URL scmUrl = new URL(personalAccessToken.getScmProviderUrl());
secret.setData(Map.of("credentials", Base64.getEncoder().encodeToString(format("%s://%s:%s@%s%s", scmUrl.getProtocol(), personalAccessToken.getScmTokenName().startsWith(OAUTH_2_PREFIX) ? "oauth2" : personalAccessToken.getScmUserName(), URLEncoder.encode(personalAccessToken.getToken(), UTF_8), scmUrl.getHost(), scmUrl.getPort() != 80 && scmUrl.getPort() != -1 ? ":" + scmUrl.getPort() : "").getBytes())));
client.secrets().inNamespace(namespace).createOrReplace(secret);
} catch (InfrastructureException | MalformedURLException e) {
throw new ScmConfigurationPersistenceException(e.getMessage(), e);
}
}
use of org.eclipse.che.api.factory.server.scm.exception.ScmConfigurationPersistenceException in project che-server by eclipse-che.
the class KubernetesPersonalAccessTokenManager method save.
@VisibleForTesting
void save(PersonalAccessToken personalAccessToken) throws UnsatisfiedScmPreconditionException, ScmConfigurationPersistenceException {
try {
String namespace = getFirstNamespace();
ObjectMeta meta = new ObjectMetaBuilder().withName(NameGenerator.generate(NAME_PATTERN, 5)).withAnnotations(new ImmutableMap.Builder<String, String>().put(ANNOTATION_CHE_USERID, personalAccessToken.getCheUserId()).put(ANNOTATION_SCM_USERID, personalAccessToken.getScmUserId()).put(ANNOTATION_SCM_USERNAME, personalAccessToken.getScmUserName()).put(ANNOTATION_SCM_URL, personalAccessToken.getScmProviderUrl()).put(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_ID, personalAccessToken.getScmTokenId()).put(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_NAME, personalAccessToken.getScmTokenName()).build()).withLabels(SECRET_LABELS).build();
Secret secret = new SecretBuilder().withMetadata(meta).withData(Map.of(TOKEN_DATA_FIELD, Base64.getEncoder().encodeToString(personalAccessToken.getToken().getBytes(StandardCharsets.UTF_8)))).build();
clientFactory.create().secrets().inNamespace(namespace).createOrReplace(secret);
} catch (KubernetesClientException | InfrastructureException e) {
throw new ScmConfigurationPersistenceException(e.getMessage(), e);
}
}
use of org.eclipse.che.api.factory.server.scm.exception.ScmConfigurationPersistenceException in project devspaces-images by redhat-developer.
the class KubernetesPersonalAccessTokenManager method get.
@Override
public Optional<PersonalAccessToken> get(Subject cheUser, String scmServerUrl) throws ScmConfigurationPersistenceException, ScmUnauthorizedException, ScmCommunicationException {
try {
for (KubernetesNamespaceMeta namespaceMeta : namespaceFactory.list()) {
List<Secret> secrets = namespaceFactory.access(null, namespaceMeta.getName()).secrets().get(KUBERNETES_PERSONAL_ACCESS_TOKEN_LABEL_SELECTOR);
for (Secret secret : secrets) {
Map<String, String> annotations = secret.getMetadata().getAnnotations();
String trimmedUrl = StringUtils.trimEnd(annotations.get(ANNOTATION_SCM_URL), '/');
if (annotations.get(ANNOTATION_CHE_USERID).equals(cheUser.getUserId()) && trimmedUrl.equals(StringUtils.trimEnd(scmServerUrl, '/'))) {
PersonalAccessToken token = new PersonalAccessToken(trimmedUrl, annotations.get(ANNOTATION_CHE_USERID), annotations.get(ANNOTATION_SCM_USERNAME), annotations.get(ANNOTATION_SCM_USERID), annotations.get(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_NAME), annotations.get(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_ID), new String(Base64.getDecoder().decode(secret.getData().get("token"))));
if (scmPersonalAccessTokenFetcher.isValid(token)) {
return Optional.of(token);
} else {
// Removing token that is no longer valid. If several tokens exist the next one could
// be valid. If no valid token can be found, the caller should react in the same way
// as it reacts if no token exists. Usually, that means that process of new token
// retrieval would be initiated.
clientFactory.create().secrets().inNamespace(namespaceMeta.getName()).delete(secret);
}
}
}
}
} catch (InfrastructureException | UnknownScmProviderException e) {
throw new ScmConfigurationPersistenceException(e.getMessage(), e);
}
return Optional.empty();
}
use of org.eclipse.che.api.factory.server.scm.exception.ScmConfigurationPersistenceException in project devspaces-images by redhat-developer.
the class KubernetesPersonalAccessTokenManager method save.
@VisibleForTesting
void save(PersonalAccessToken personalAccessToken) throws UnsatisfiedScmPreconditionException, ScmConfigurationPersistenceException {
try {
String namespace = getFirstNamespace();
ObjectMeta meta = new ObjectMetaBuilder().withName(NameGenerator.generate(NAME_PATTERN, 5)).withAnnotations(new ImmutableMap.Builder<String, String>().put(ANNOTATION_CHE_USERID, personalAccessToken.getCheUserId()).put(ANNOTATION_SCM_USERID, personalAccessToken.getScmUserId()).put(ANNOTATION_SCM_USERNAME, personalAccessToken.getScmUserName()).put(ANNOTATION_SCM_URL, personalAccessToken.getScmProviderUrl()).put(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_ID, personalAccessToken.getScmTokenId()).put(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_NAME, personalAccessToken.getScmTokenName()).build()).withLabels(SECRET_LABELS).build();
Secret secret = new SecretBuilder().withMetadata(meta).withData(Map.of(TOKEN_DATA_FIELD, Base64.getEncoder().encodeToString(personalAccessToken.getToken().getBytes(StandardCharsets.UTF_8)))).build();
clientFactory.create().secrets().inNamespace(namespace).createOrReplace(secret);
} catch (KubernetesClientException | InfrastructureException e) {
throw new ScmConfigurationPersistenceException(e.getMessage(), e);
}
}
use of org.eclipse.che.api.factory.server.scm.exception.ScmConfigurationPersistenceException in project che-server by eclipse-che.
the class KubernetesPersonalAccessTokenManager method get.
@Override
public Optional<PersonalAccessToken> get(Subject cheUser, String scmServerUrl) throws ScmConfigurationPersistenceException, ScmUnauthorizedException, ScmCommunicationException {
try {
for (KubernetesNamespaceMeta namespaceMeta : namespaceFactory.list()) {
List<Secret> secrets = namespaceFactory.access(null, namespaceMeta.getName()).secrets().get(KUBERNETES_PERSONAL_ACCESS_TOKEN_LABEL_SELECTOR);
for (Secret secret : secrets) {
Map<String, String> annotations = secret.getMetadata().getAnnotations();
String trimmedUrl = StringUtils.trimEnd(annotations.get(ANNOTATION_SCM_URL), '/');
if (annotations.get(ANNOTATION_CHE_USERID).equals(cheUser.getUserId()) && trimmedUrl.equals(StringUtils.trimEnd(scmServerUrl, '/'))) {
PersonalAccessToken token = new PersonalAccessToken(trimmedUrl, annotations.get(ANNOTATION_CHE_USERID), annotations.get(ANNOTATION_SCM_USERNAME), annotations.get(ANNOTATION_SCM_USERID), annotations.get(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_NAME), annotations.get(ANNOTATION_SCM_PERSONAL_ACCESS_TOKEN_ID), new String(Base64.getDecoder().decode(secret.getData().get("token"))));
if (scmPersonalAccessTokenFetcher.isValid(token)) {
return Optional.of(token);
} else {
// Removing token that is no longer valid. If several tokens exist the next one could
// be valid. If no valid token can be found, the caller should react in the same way
// as it reacts if no token exists. Usually, that means that process of new token
// retrieval would be initiated.
clientFactory.create().secrets().inNamespace(namespaceMeta.getName()).delete(secret);
}
}
}
}
} catch (InfrastructureException | UnknownScmProviderException e) {
throw new ScmConfigurationPersistenceException(e.getMessage(), e);
}
return Optional.empty();
}
Aggregations