/**
   * Insert the ProductRelease in SDC.
   *
   * @param productReleaseDto
   * @throws AlreadyExistsProductReleaseException
   * @throws InvalidProductReleaseException
   * @return proudctRelease
   */
  public ProductRelease insert(String pName, ProductReleaseDto productReleaseDto)
      throws AlreadyExistsProductReleaseException, InvalidProductReleaseException {

    try {
      generalValidator.validateName(pName);
    } catch (InvalidNameException e) {
      throw new InvalidProductReleaseException(e.getMessage());
    }
    productReleaseDto.setProductName(pName);

    log.info(
        "Inserting a new product release in the software catalogue "
            + productReleaseDto.getProductName()
            + " "
            + productReleaseDto.getVersion()
            + " "
            + productReleaseDto.getProductDescription());
    Product product =
        new Product(productReleaseDto.getProductName(), productReleaseDto.getProductDescription());

    ProductRelease productRelease =
        new ProductRelease(
            productReleaseDto.getVersion(),
            productReleaseDto.getReleaseNotes(),
            product,
            productReleaseDto.getSupportedOS(),
            productReleaseDto.getTransitableReleases());

    log.info(productRelease.toString());
    return productReleaseManager.insert(productRelease);
  }
  /** {@inheritDoc} */
  @Override
  public ProductRelease update(
      ProductReleaseDto releaseDto, InputStream cookbook, InputStream files) {
    try {

      MultiPart payload =
          new MultiPart()
              .bodyPart(new BodyPart(releaseDto, MediaType.valueOf(getType())))
              .bodyPart(
                  new BodyPart(
                      IOUtils.toByteArray(cookbook), MediaType.APPLICATION_OCTET_STREAM_TYPE))
              .bodyPart(
                  new BodyPart(
                      IOUtils.toByteArray(files), MediaType.APPLICATION_OCTET_STREAM_TYPE));

      String url =
          getBaseHost()
              + MessageFormat.format(
                  ClientConstants.PRODUCT_RELEASE_PATH,
                  releaseDto.getProductName(),
                  releaseDto.getVersion());
      WebResource wr = getClient().resource(url);
      return wr.accept(getType()).type("multipart/mixed").entity(payload).put(ProductRelease.class);
    } catch (FileNotFoundException e) {
      throw new RuntimeException(e);
    } catch (IOException e) {
      throw new RuntimeException(e);
    }
  }
 @Override
 public ProductRelease add(ProductReleaseDto productReleaseDto) {
   String url =
       getBaseHost()
           + MessageFormat.format(
               ClientConstants.BASE_PRODUCT_RELEASE_PATH, productReleaseDto.getProductName());
   WebResource wr = getClient().resource(url);
   return wr.accept(getType()).type(getType()).post(ProductRelease.class, productReleaseDto);
 }
  /**
   * Update the ProductRelease (productReleaseDto, cookbooks, installable).
   *
   * @param multipart
   * @throws ProductReleaseNotFoundException
   * @throws InvalidProductReleaseException
   * @throws InvalidProductReleaseException
   * @throws InvalidMultiPartRequestException
   * @return productRelease
   * @throws InvalidProductReleaseUpdateRequestException
   */
  public ProductRelease update(MultiPart multiPart)
      throws ProductReleaseNotFoundException, InvalidProductReleaseException,
          InvalidMultiPartRequestException, InvalidProductReleaseUpdateRequestException {

    ProductReleaseDto productReleaseDto =
        multiPart.getBodyParts().get(0).getEntityAs(ProductReleaseDto.class);
    log.log(
        Level.INFO,
        "ProductRelease "
            + productReleaseDto.getProductName()
            + " version "
            + productReleaseDto.getVersion());

    // TODO Validar el Objeto ProductReleaseDto en las validaciones
    Product product = new Product();
    ProductRelease productRelease = new ProductRelease();

    product.setName(productReleaseDto.getProductName());

    if (productReleaseDto.getProductDescription() != null) {
      product.setDescription(productReleaseDto.getProductDescription());
    }

    /*
     * if (productReleaseDto.getPrivateAttributes() != null) { for (int i =
     * 0; productReleaseDto.getPrivateAttributes().size() < 1; i++) {
     * product
     * .addAttribute(productReleaseDto.getPrivateAttributes().get(i)); } }
     */

    productRelease.setProduct(product);

    if (productReleaseDto.getVersion() != null) {
      productRelease.setVersion(productReleaseDto.getVersion());
    }

    // ReleaseNotes
    if (productReleaseDto.getReleaseNotes() != null) {
      productRelease.setReleaseNotes(productReleaseDto.getReleaseNotes());
    }

    // PrivateAttributes
    /*
     * if (productReleaseDto.getPrivateAttributes() != null) {
     * productRelease
     * .setPrivateAttributes(productReleaseDto.getPrivateAttributes()); }
     */

    // SupportedOS
    if (productReleaseDto.getSupportedOS() != null) {
      productRelease.setSupportedOOSS(productReleaseDto.getSupportedOS());
    }

    // TransitableRelease
    if (productReleaseDto.getTransitableReleases() != null) {
      productRelease.setTransitableReleases(productReleaseDto.getTransitableReleases());
    }

    ReleaseDto releaseDto =
        new ReleaseDto(
            productReleaseDto.getProductName(), productReleaseDto.getVersion(), "product");

    validator.validateUpdate(releaseDto, multiPart);

    File cookbook = null;
    File installable = null;

    try {
      cookbook =
          File.createTempFile(
              "cookbook-" + releaseDto.getName() + "-" + releaseDto.getVersion() + ".tar", ".tmp");
      cookbook =
          getFileFromBodyPartEntity(
              (BodyPartEntity) multiPart.getBodyParts().get(1).getEntity(), cookbook);
    } catch (IOException e) {
      throw new SdcRuntimeException(e);
    }

    try {
      installable =
          File.createTempFile(
              "installable-" + releaseDto.getName() + "-" + releaseDto.getVersion() + ".tar",
              ".tmp");

      installable =
          getFileFromBodyPartEntity(
              (BodyPartEntity) multiPart.getBodyParts().get(2).getEntity(), installable);
    } catch (IOException e) {
      throw new SdcRuntimeException(e);
    }

    return productReleaseManager.update(
        productRelease, cookbook, installable, getCredentials().getToken());
  }
  /**
   * {@inheritDoc}
   *
   * @throws InvalidProductReleaseUpdateRequestException
   * @throws InvalidMultiPartRequestException
   */
  public ProductRelease insert(MultiPart multiPart)
      throws AlreadyExistsProductReleaseException, InvalidProductReleaseException,
          InvalidMultiPartRequestException {

    validator.validateInsert(multiPart);

    File cookbook = null;
    File installable = null;

    // First part contains a Project object
    ProductReleaseDto productReleaseDto =
        multiPart.getBodyParts().get(0).getEntityAs(ProductReleaseDto.class);
    log.log(
        Level.INFO,
        " Insert ProductRelease "
            + productReleaseDto.getProductName()
            + " version "
            + productReleaseDto.getVersion());

    Product product =
        new Product(productReleaseDto.getProductName(), productReleaseDto.getProductDescription());

    /*
     * for (int i = 0; productReleaseDto.getPrivateAttributes().size() < 1;
     * i++) {
     * product.addAttribute(productReleaseDto.getPrivateAttributes().get
     * (i)); }
     */

    ProductRelease productRelease =
        new ProductRelease(
            productReleaseDto.getVersion(),
            productReleaseDto.getReleaseNotes(),
            // productReleaseDto.getPrivateAttributes(),
            product,
            productReleaseDto.getSupportedOS(),
            productReleaseDto.getTransitableReleases());

    try {
      cookbook =
          File.createTempFile(
              "cookbook-"
                  + productReleaseDto.getProductName()
                  + "-"
                  + productReleaseDto.getVersion()
                  + ".tar",
              ".tmp");

      installable =
          File.createTempFile(
              "installable-"
                  + productReleaseDto.getProductName()
                  + "-"
                  + productReleaseDto.getVersion()
                  + ".tar",
              ".tmp");

      cookbook =
          getFileFromBodyPartEntity(
              (BodyPartEntity) multiPart.getBodyParts().get(1).getEntity(), cookbook);
      installable =
          getFileFromBodyPartEntity(
              (BodyPartEntity) multiPart.getBodyParts().get(2).getEntity(), installable);
    } catch (IOException e) {
      throw new RuntimeException(e);
    }

    return productReleaseManager.insert(
        productRelease, cookbook, installable, getCredentials().getToken());
  }