

As traduções são geradas por tradução automática. Em caso de conflito entre o conteúdo da tradução e da versão original em inglês, a versão em inglês prevalecerá.

# Integrando seu produto de contêiner com o AWS Marketplace Metering Service usando o AWS SDK para Java
<a name="java-integration-example-registerusage"></a>

Você pode usar o AWS SDK para Java para se integrar ao AWS Marketplace Metering Service. A medição contínua para uso do software é feita automaticamente pelo. AWS Marketplace Metering Control Plane O software não precisa realizar ações específicas de medição, exceto chamar `RegisterUsage` uma vez para medição do uso de software para iniciar. Este tópico fornece um exemplo de implementação usando o AWS SDK para Java para integrar com a `RegisterUsage` ação do [AWS Marketplace Metering Service](https://docs.aws.amazon.com/marketplacemetering/latest/APIReference/Welcome.html). 

`RegisterUsage` deve ser chamado imediatamente no momento de execução de um contêiner. Se você não registrar o contêiner nas primeiras 6 horas após a execução do contêiner, o Serviço de medição do AWS Marketplace não fornecerá nenhuma garantia de medição dos meses anteriores. No entanto, a medição continuará durante o mês atual até que o contêiner termine.

Para obter o código-fonte completo, consulte [RegisterUsage Exemplo de Java](#registerusage-java-example). Muitas dessas etapas se aplicam independentemente da linguagem do AWS SDK. 



**Exemplos de etapa para a integração do Serviço de medição do AWS Marketplace**

1. Faça login no [Portal de gerenciamento do AWS Marketplace](https://aws.amazon.com/marketplace/management/tour).

1. Em **Assets (Ativos)**, selecione **Containers (Contêineres)** para começar a criar um produto de contêiner. A criação do produto gera o código para a integração do produto com a imagem de contêiner. Para obter mais informações sobre configuração de permissões do IAM, consulte [AWS Marketplace permissões da API de medição e titulação](iam-user-policy-for-aws-marketplace-actions.md).

1.  Faça download do [SDK do AWS Java](https://aws.amazon.com/sdk-for-java/) público. 
**Importante**  
 Para chamar a medição APIs do Amazon EKS, você deve [usar um AWS SDK compatível e executar em um](https://docs.aws.amazon.com/eks/latest/userguide/iam-roles-for-service-accounts-minimum-sdk.html) cluster do Amazon EKS executando o Kubernetes 1.13 ou posterior. 

1.  (Opcional) Se você estiver se integrando à `RegisterUsage` ação e quiser realizar a verificação de assinatura digital, precisará configurar a biblioteca de verificação de [BouncyCastle](https://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk15on)assinatura no caminho de classe do seu aplicativo.

   Se quiser usar JSON Web Token (JWT), você também deverá incluir bibliotecas [JWT Java](https://jwt.io/) no caminho de classe do aplicativo. O uso do JWT fornece uma abordagem mais simples para a verificação de assinaturas, mas não é obrigatório. Em vez disso, você pode usar o modo autônomo BouncyCastle . Se você usa o JWT ou BouncyCastle precisa usar um sistema de compilação como o Maven para incluir dependências transitivas do BouncyCastle ou do JWT no caminho de classe do seu aplicativo.

   ```
   // Required for signature verification using code sample
   <dependency>
       <groupId>org.bouncycastle</groupId>
       <artifactId>bcpkix-jdk15on</artifactId>
       <version>1.60</version>
   </dependency>
   
   // This one is only required for JWT
   <dependency>
       <groupId>com.nimbusds</groupId>
       <artifactId>nimbus-jose-jwt</artifactId>
       <version>6.0</version>
   </dependency>
   ```

1.  Chame `RegisterUsage` de cada imagem de contêiner paga na oferta do produto. `ProductCode` e `PublicKeyVersion` são parâmetros obrigatórios, e todas as outras entradas são opcionais. Esta é uma carga útil de exemplo para `RegisterUsage`. 

   ```
   {
       "ProductCode" : "string", // (required)
       "PublicKeyVersion": 1,    // (required)
       "Nonce": "string",        // (optional) to scope down the registration
                                 //            to a specific running software
                                 //            instance and guard against
                                 //            replay attacks
   }
   ```
**nota**  
É possível ver problemas transitórios na conexão com o Serviço de medição do AWS Marketplace. O AWS Marketplace recomenda fortemente a implementação de novas tentativas por até 30 minutos, com recuo exponencial, para evitar interrupções de curto prazo ou problemas de rede.

1.  `RegisterUsage` gera uma assinatura digital RSA-PSS usando SHA-256 que é possível usar para verificar a autenticidade da solicitação. A assinatura inclui os seguintes campos: `ProductCode`, `PublicKeyVersion` e `Nonce`. Para verificar a assinatura digital, você deve manter esses campos da solicitação. Este código é uma resposta de exemplo para uma chamada `RegisterUsage`. 

   ```
   {
   "Signature": "<<JWT Token>>"
   }
   
   // Where the JWT Token is composed of 3 dot-separated, 
   // base-64 URL Encoded sections.
   // e.g. eyJhbGcVCJ9.eyJzdWIMzkwMjJ9.rrO9Qw0SXRWTe
   
   // Section 1: Header/Algorithm
   {
   "alg": "PS256",
   "typ": "JWT"
   }
   
   // Section 2: Payload
   {
   "ProductCode" : "string",
   "PublicKeyVersion": 1,
   "Nonce": "string",
   "iat": date // JWT issued at claim 
   }
   
   // Section 3: RSA-PSS SHA256 signature
   "rrO9Q4FEi3gweH3X4lrt2okf5zwIatUUwERlw016wTy_21Nv8S..."
   ```

1. Recompile uma nova versão da imagem de contêiner que inclua a chamada `RegisterUsage`, marque o contêiner e o envie para qualquer registro que seja compatível com o Amazon ECS ou o Amazon EKS, como o Amazon ECR ou o Amazon ECR Public. Se você estiver usando o Amazon ECR, verifique se a conta que executa a tarefa do Amazon ECS ou o pod do Amazon EKS tem permissões no repositório do Amazon ECR. Caso contrário, ocorrerá uma falha na inicialização.

1.  Crie um perfil do [IAM](https://aws.amazon.com/iam/) que conceda permissão para o contêiner chamar `RegisterUsage`, conforme definido no código a seguir. Forneça esse perfil do IAM no parâmetro [Função da tarefa](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task_definition_parameters.html#task_role_arn) da definição de tarefa do Amazon ECS ou de pod do Amazon EKS.

------
#### [ JSON ]

****  

   ```
   {
       "Version":"2012-10-17",		 	 	 
       "Statement": [
           {
               "Action": [
                   "aws-marketplace:RegisterUsage"
                   ],
                   "Effect": "Allow",
                   "Resource": "*"
           }
       ]
   }
   ```

------

1. Crie uma tarefa do Amazon ECS ou uma definição de pod do Amazon EKS que faça referência ao contêiner que se integrou AWS Marketplace e faça referência à função do IAM que você criou na etapa 7. Você deve habilitar o AWS CloudTrail registro na definição da tarefa se quiser ver o registro. 

1. Crie um cluster do Amazon ECS ou Amazon EKS para executar sua tarefa ou pod. Para obter mais informações sobre como criar um cluster do Amazon ECS, consulte [Criar um cluster](https://docs.aws.amazon.com/AmazonECS/latest/userguide/create_cluster.html) no *Guia do desenvolvedor do Amazon Elastic Container Service*. Para obter mais informações sobre como criar um cluster do Amazon EKS (usando o Kubernetes versão 1.1.3.x ou posterior), consulte [Criar um cluster do Amazon EKS](https://docs.aws.amazon.com/eks/latest/userguide/create_cluster.html).

1. Configure o cluster Amazon ECS ou Amazon EKS e inicie a definição de tarefa do Amazon ECS ou o pod Amazon EKS que você criou, no us-east-1. Região da AWSÉ somente durante este processo de teste, antes de o produto estar ativo, que você precisa usar essa região.

1. Você pode começar a criar seu produto de contêiner assim que obtiver uma resposta válida de `RegisterUsage`. Se tiver dúvidas, entre em contato com a equipe de [Operações do vendedor do AWS Marketplace](https://aws.amazon.com/marketplace/management/contact-us/). 

## RegisterUsage Exemplo de Java
<a name="registerusage-java-example"></a>

O exemplo a seguir usa o AWS SDK para Java e AWS Marketplace Metering Service para chamar a `RegisterUsage` operação. A verificação de assinatura é opcional, mas se quiser executar a verificação de assinatura, você deverá incluir as bibliotecas de verificação de assinatura digital obrigatórias. Esse exemplo é apenas para fins de ilustração. 

```
import com.amazonaws.auth.PEM;
import com.amazonaws.services.marketplacemetering.AWSMarketplaceMetering;
import com.amazonaws.services.marketplacemetering.AWSMarketplaceMeteringClientBuilder;
import com.amazonaws.services.marketplacemetering.model.RegisterUsageRequest;
import com.amazonaws.services.marketplacemetering.model.RegisterUsageResult;
import com.amazonaws.util.json.Jackson;
import com.fasterxml.jackson.databind.JsonNode;
import com.nimbusds.jose.JWSObject;
import com.nimbusds.jose.JWSVerifier;
import com.nimbusds.jose.crypto.RSASSAVerifier;
import java.io.ByteArrayInputStream;
import java.nio.charset.StandardCharsets;
import java.security.PublicKey;
import java.security.Security;
import java.security.Signature;
import java.security.interfaces.RSAPublicKey;
import java.util.Base64;
import java.util.Optional;
import java.util.UUID;
import org.bouncycastle.jce.provider.BouncyCastleProvider;

/**
 * Class for making calls out to &MKT; Metering Service.
 */
class RegisterUsage {

    private static final String PRODUCT_CODE = ".......";

    private final AWSMarketplaceMetering registerUsageClient;
    private final SignatureVerifier signatureVerifier;
    private final int publicKeyVersion;

    public RegisterUsage(final SignatureVerifier signatureVerifier) {
        this.signatureVerifier = signatureVerifier;
        this.publicKeyVersion = PublicKeyProvider.PUBLIC_KEY_VERSION;
        this.registerUsageClient = AWSMarketplaceMeteringClientBuilder.standard().build();
    }

    /**
     * Shows how to call RegisterUsage client and verify digital signature.
     */
    public void callRegisterUsage() {
        RegisterUsageRequest request = new RegisterUsageRequest()
                .withProductCode(PRODUCT_CODE)
                .withPublicKeyVersion(publicKeyVersion)
                .withNonce(UUID.randomUUID().toString());

        // Execute call to RegisterUsage (only need to call once at container startup)
        RegisterUsageResult result = this.registerUsageClient.registerUsage(request);

        // Verify Digital Signature w/o JWT
        boolean isSignatureValid = this.signatureVerifier.verify(request, result);
        if (!isSignatureValid) {
            throw new RuntimeException("Revoke entitlement, digital signature invalid.");
        }
    }
}

/**
 * Signature verification class with both a JWT-library based verification
 * and a non-library based implementation.
 */
class SignatureVerifier {
    private static BouncyCastleProvider BC = new BouncyCastleProvider();

    private static final String SIGNATURE_ALGORITHM = "SHA256withRSA/PSS";

    private final PublicKey publicKey;

    public SignatureVerifier(PublicKeyProvider publicKeyProvider) {
        this.publicKey = publicKeyProvider.getPublicKey().orElse(null);
        Security.addProvider(BC);
    }

    /**
     * Example signature verification using the NimbusJOSEJWT library to verify the JWT Token.
     *
     * @param request RegisterUsage Request.
     * @param result  RegisterUsage Result.
     * @return true if the token matches.
     */
    public boolean verifyUsingNimbusJOSEJWT(final RegisterUsageRequest request, final RegisterUsageResult result) {
        if (!getPublicKey().isPresent()) {
            return false;
        }

        try {
            JWSVerifier verifier = new RSASSAVerifier((RSAPublicKey) getPublicKey().get());
            JWSObject jwsObject = JWSObject.parse(result.getSignature());
            return jwsObject.verify(verifier) && validatePayload(jwsObject.getPayload().toString(), request, result);
        } catch (Exception e) {
            // log error
            return false;
        }
    }

    /**
     * Example signature verification without any JWT library support.
     *
     * @param request RegisterUsage Request.
     * @param result  RegisterUsage Result.
     * @return true if the token matches.
     */
    public boolean verify(final RegisterUsageRequest request, final RegisterUsageResult result) {
        if (!getPublicKey().isPresent()) {
            return false;
        }
        try {
            String[] jwtParts = result.getSignature().split("\\.");
            String header = jwtParts[0];
            String payload = jwtParts[1];
            String payloadSignature = jwtParts[2];

            Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM, BC);
            signature.initVerify(getPublicKey().get());
            signature.update(String.format("%s.%s", header, payload).getBytes(StandardCharsets.UTF_8));
            boolean verified = signature.verify(Base64.getUrlDecoder()
                    .decode(payloadSignature.getBytes(StandardCharsets.UTF_8)));

            String decodedPayload = new String(Base64.getUrlDecoder().decode(payload));
            return verified && validatePayload(decodedPayload, request, result);
        } catch (Exception e) {
            // log error
            return false;
        }
    }

    /**
     * Validate each value in the returned payload matches values originally
     * supplied in the request to RegisterUsage. TimeToLiveInMillis and
     * PublicKeyExpirationTimestamp will have the values in the payload compared
     * to values in the signature
     */
    private boolean validatePayload(final String payload, final RegisterUsageRequest request,
                                    final RegisterUsageResult result) {
        try {
            JsonNode payloadJson = Jackson.getObjectMapper().readTree(payload);
            boolean matches = payloadJson.get("productCode")
                    .asText()
                    .equals(request.getProductCode());
            matches = matches && payloadJson.get("nonce")
                    .asText()
                    .equals(request.getNonce());
            return matches = matches && payloadJson.get("publicKeyVersion")
                    .asText()
                    .equals(String.valueOf(request.getPublicKeyVersion()));

        } catch (Exception ex) {
            // log error
            return false;
        }
    }

    private Optional<PublicKey> getPublicKey() {
        return Optional.ofNullable(this.publicKey);
    }
}

/**
 * Public key provider taking advantage of the &AWS; PEM Utility.
 */
class PublicKeyProvider {
    // Replace with your public key. Ensure there are new-lines ("\n") in the
    // string after "-----BEGIN PUBLIC KEY-----\n" and before "\n-----END PUBLIC KEY-----".
    private static final String PUBLIC_KEY =
            "-----BEGIN PUBLIC KEY-----\n"
                    + "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDdlatRjRjogo3WojgGHFHYLugd\n"
                    + "UWAY9iR3fy4arWNA1KoS8kVw33cJibXr8bvwUAUparCwlvdbH6dvEOfou0/gCFQs\n"
                    + "HUfQrSDv+MuSUMAe8jzKE4qW+jK+xQU9a03GUnKHkkle+Q0pX/g6jXZ7r1/xAK5D\n"
                    + "o2kQ+X5xK9cipRgEKwIDAQAB\n"
                    + "-----END PUBLIC KEY-----";

    public static final int PUBLIC_KEY_VERSION = 1;

    public Optional<PublicKey> getPublicKey() {
        try {
            return Optional.of(PEM.readPublicKey(new ByteArrayInputStream(
                    PUBLIC_KEY.getBytes(StandardCharsets.UTF_8))));
        } catch (Exception e) {
            // log error
            return Optional.empty();
        }
    }
}
```