use of org.candlepin.model.dto.ProductContentData in project candlepin by candlepin.
the class CandlepinPoolManager method refreshPoolsWithRegeneration.
/*
* We need to update/regen entitlements in the same transaction we update pools
* so we don't miss anything
*/
@Transactional
@SuppressWarnings("checkstyle:methodlength")
@Traceable
void refreshPoolsWithRegeneration(SubscriptionServiceAdapter subAdapter, @TraceableParam("owner") Owner owner, boolean lazy) {
Date now = new Date();
owner = this.resolveOwner(owner);
log.info("Refreshing pools for owner: {}", owner);
Map<String, Subscription> subscriptionMap = new HashMap<>();
Map<String, ProductData> productMap = new HashMap<>();
Map<String, ContentData> contentMap = new HashMap<>();
// Resolve all our subscriptions, products and content to ensure we don't have bad or
// duplicate inbound data
log.debug("Fetching subscriptions from adapter...");
List<Subscription> subscriptions = subAdapter.getSubscriptions(owner);
log.debug("Done. Processing subscriptions...");
for (Subscription subscription : subscriptions) {
if (subscription == null) {
continue;
}
if (subscription.getId() == null) {
log.error("subscription does not contain a mappable ID: {}", subscription);
throw new IllegalStateException("subscription does not contain a mappable ID: " + subscription);
}
Subscription existingSub = subscriptionMap.get(subscription.getId());
if (existingSub != null && !existingSub.equals(subscription)) {
log.warn("Multiple versions of the same subscription received during refresh; " + "discarding duplicate: {} => {}, {}", subscription.getId(), existingSub, subscription);
continue;
}
subscriptionMap.put(subscription.getId(), subscription);
List<ProductData> products = new LinkedList<>();
products.add(subscription.getProduct());
products.add(subscription.getDerivedProduct());
products.addAll(subscription.getProvidedProducts());
products.addAll(subscription.getDerivedProvidedProducts());
for (ProductData product : products) {
if (product == null) {
// forward.
continue;
}
if (product.getId() == null) {
log.error("product does not contain a mappable Red Hat ID: {}", product);
throw new IllegalStateException("product does not contain a mappable Red Hat ID: " + product);
}
// Product is coming from an upstream source; lock it so only upstream can make
// further changes to it.
product.setLocked(true);
ProductData existingProduct = productMap.get(product.getId());
if (existingProduct != null && !existingProduct.equals(product)) {
log.warn("Multiple versions of the same product received during refresh; " + "discarding duplicate: {} => {}, {}", product.getId(), existingProduct, product);
} else {
productMap.put(product.getId(), product);
Collection<ProductContentData> pcdCollection = product.getProductContent();
if (pcdCollection != null) {
for (ProductContentData pcd : pcdCollection) {
if (pcd == null) {
log.error("product contains a null product-content mapping: {}", product);
throw new IllegalStateException("product contains a null product-content mapping: " + product);
}
ContentData content = pcd.getContent();
// population validation for us.
if (content == null || content.getId() == null) {
log.error("product contains a null or incomplete product-content mapping: {}", product);
throw new IllegalStateException("product contains a null or incomplete " + "product-content mapping: " + product);
}
// We need to lock the incoming content here, but doing so will affect
// the equality comparison for products. We'll correct them later.
ContentData existingContent = contentMap.get(content.getId());
if (existingContent != null && !existingContent.equals(content)) {
log.warn("Multiple versions of the same content received during refresh; " + "discarding duplicate: {} => {}, {}", content.getId(), existingContent, content);
} else {
contentMap.put(content.getId(), content);
}
}
}
}
}
}
// Persist content changes
log.debug("Importing {} content...", contentMap.size());
// TODO: Find a more efficient way of doing this, preferably within this method
for (ContentData cdata : contentMap.values()) {
cdata.setLocked(true);
}
Map<String, Content> importedContent = this.contentManager.importContent(owner, contentMap, productMap.keySet()).getImportedEntities();
log.debug("Importing {} product(s)...", productMap.size());
ImportResult<Product> importResult = this.productManager.importProducts(owner, productMap, importedContent);
Map<String, Product> importedProducts = importResult.getImportedEntities();
Map<String, Product> updatedProducts = importResult.getUpdatedEntities();
log.debug("Refreshing {} pool(s)...", subscriptionMap.size());
Iterator<Map.Entry<String, Subscription>> subsIterator = subscriptionMap.entrySet().iterator();
while (subsIterator.hasNext()) {
Map.Entry<String, Subscription> entry = subsIterator.next();
Subscription sub = entry.getValue();
if (now.after(sub.getEndDate())) {
log.info("Skipping expired subscription: {}", sub);
subsIterator.remove();
continue;
}
log.debug("Processing subscription: {}", sub);
Pool pool = this.convertToMasterPoolImpl(sub, owner, importedProducts);
this.refreshPoolsForMasterPool(pool, false, lazy, updatedProducts);
}
// delete pools whose subscription disappeared:
log.debug("Deleting pools for absent subscriptions...");
List<Pool> poolsToDelete = new ArrayList<>();
for (Pool pool : poolCurator.getPoolsFromBadSubs(owner, subscriptionMap.keySet())) {
if (this.isManaged(pool)) {
poolsToDelete.add(pool);
}
}
deletePools(poolsToDelete);
// TODO: break this call into smaller pieces. There may be lots of floating pools
log.debug("Updating floating pools...");
List<Pool> floatingPools = poolCurator.getOwnersFloatingPools(owner);
updateFloatingPools(floatingPools, lazy, updatedProducts);
log.info("Refresh pools for owner: {} completed in: {}ms", owner.getKey(), System.currentTimeMillis() - now.getTime());
}
use of org.candlepin.model.dto.ProductContentData in project candlepin by candlepin.
the class DefaultEntitlementCertServiceAdapterTest method setupEntitlements.
private void setupEntitlements(String consumerArch, String certVersion) {
consumer.setFact("system.certificate_version", certVersion);
consumer.setFact("uname.machine", consumerArch);
ProductData pdata = subscription.getProduct();
pdata.setAttribute(Product.Attributes.WARNING_PERIOD, "20");
pdata.setAttribute(Product.Attributes.SOCKETS, "4");
pdata.setAttribute(Product.Attributes.RAM, "8");
pdata.setAttribute(Product.Attributes.CORES, "4");
pdata.setAttribute(Product.Attributes.MANAGEMENT_ENABLED, "true");
pdata.setAttribute(Product.Attributes.STACKING_ID, "45678");
entitlement.getPool().setAttribute(Product.Attributes.VIRT_ONLY, "true");
pdata.setAttribute(Product.Attributes.SUPPORT_LEVEL, "slevel");
pdata.setAttribute(Product.Attributes.SUPPORT_TYPE, "stype");
subscription.setAccountNumber("account1");
subscription.setContractNumber("contract1");
subscription.setOrderNumber("order1");
if (pdata.getProductContent() != null) {
for (ProductContentData pcd : pdata.getProductContent()) {
pcd.setEnabled(false);
}
}
}
use of org.candlepin.model.dto.ProductContentData in project candlepin by candlepin.
the class ProductDTOTranslatorTest method verifyOutput.
@Override
protected void verifyOutput(ProductDTO source, ProductData dto, boolean childrenGenerated) {
if (source != null) {
assertEquals(source.getUuid(), dto.getUuid());
assertEquals(source.getId(), dto.getId());
assertEquals(source.getName(), dto.getName());
assertEquals(source.getMultiplier(), dto.getMultiplier());
assertEquals(source.getAttributes(), dto.getAttributes());
assertEquals(source.getDependentProductIds(), dto.getDependentProductIds());
assertNotNull(dto.getProductContent());
if (childrenGenerated) {
for (ProductContentDTO pcdto : source.getProductContent()) {
for (ProductContentData pcdata : dto.getProductContent()) {
ContentDTO cdto = pcdto.getContent();
ContentData cdata = pcdata.getContent();
assertNotNull(cdata);
assertNotNull(cdata.getUuid());
if (cdata.getUuid().equals(cdto.getUuid())) {
assertEquals(pcdto.isEnabled(), pcdata.isEnabled());
// Pass the content off to the ContentTranslatorTest to verify it
this.contentDTOTranslatorTest.verifyOutput(cdto, cdata, true);
}
}
}
} else {
assertTrue(dto.getProductContent().isEmpty());
}
} else {
assertNull(dto);
}
}
use of org.candlepin.model.dto.ProductContentData in project candlepin by candlepin.
the class ContentManager method removeContentByUuids.
/**
* Removes all content with the provided UUIDs from the given owner.
*
* @param owner
* The owner from which to remove content
*
* @param contentUuids
* A collection of UUIDs representing the content to remove
*
* @param regenerateEntitlementCerts
* Whether or not changes made to the content should trigger the regeneration of entitlement
* certificates for affected consumers
*
* @throws IllegalArgumentException
* if owner is null
*/
public void removeContentByUuids(Owner owner, Collection<String> contentUuids, boolean regenerateEntitlementCerts) {
if (owner == null) {
throw new IllegalArgumentException("owner is null");
}
if (contentUuids != null && !contentUuids.isEmpty()) {
log.debug("Deleting content with UUIDs: {}", contentUuids);
List<Product> affectedProducts = this.productCurator.getProductsByContentUuids(owner, contentUuids).list();
if (!affectedProducts.isEmpty()) {
log.debug("Updating {} affected products", affectedProducts.size());
if (!(contentUuids instanceof Set)) {
// Convert this to a set so our filtering lookups aren't painfully slow
contentUuids = new HashSet<>(contentUuids);
}
// Get the collection of content those products use, throwing out the ones we'll be
// removing shortly
Map<String, Content> affectedProductsContent = new HashMap<>();
for (Content content : this.contentCurator.getContentByProducts(affectedProducts)) {
if (!contentUuids.contains(content.getUuid())) {
affectedProductsContent.put(content.getId(), content);
}
}
// Convert our affectedProducts into DTOs (hoping Hibernate uses its entity cache
// instead of pulling down the content list for each product...)
Map<String, ProductData> affectedProductData = new HashMap<>();
for (Product product : affectedProducts) {
ProductData pdto = product.toDTO();
Iterator<ProductContentData> pcd = pdto.getProductContent().iterator();
while (pcd.hasNext()) {
ContentData cdto = pcd.next().getContent();
if (!affectedProductsContent.containsKey(cdto.getId())) {
pcd.remove();
}
}
affectedProductData.put(pdto.getId(), pdto);
}
// Perform a micro-import for these products using the content map we just built
log.debug("Performing micro-import for products: {}", affectedProductData);
this.productManager.importProducts(owner, affectedProductData, affectedProductsContent);
if (regenerateEntitlementCerts) {
this.entitlementCertGenerator.regenerateCertificatesOf(Arrays.asList(owner), affectedProducts, true);
}
}
// Remove content references
this.ownerContentCurator.removeOwnerContentReferences(owner, contentUuids);
}
}
use of org.candlepin.model.dto.ProductContentData in project candlepin by candlepin.
the class Entitler method getDevProductMap.
/**
* Looks up all Products matching the specified SKU and the consumer's
* installed products.
*
* @param consumer the consumer to pull the installed product id list from.
* @param sku the product id of the SKU.
* @return a {@link DeveloperProducts} object that contains the Product objects
* from the adapter.
*/
private DeveloperProducts getDevProductMap(Consumer consumer, Owner owner, String sku) {
List<String> devProductIds = new ArrayList<>();
devProductIds.add(sku);
for (ConsumerInstalledProduct ip : consumer.getInstalledProducts()) {
devProductIds.add(ip.getProductId());
}
Map<String, ProductData> productMap = new HashMap<>();
Map<String, ContentData> contentMap = new HashMap<>();
log.debug("Importing products for dev pool resolution...");
for (ProductData product : this.productAdapter.getProductsByIds(owner, devProductIds)) {
if (product == null) {
continue;
}
if (sku.equals(product.getId()) && StringUtils.isEmpty(product.getAttributeValue(Product.Attributes.SUPPORT_LEVEL))) {
// if there is no SLA, apply the default
product.setAttribute(Product.Attributes.SUPPORT_LEVEL, this.DEFAULT_DEV_SLA);
}
// Product is coming from an upstream source; lock it so only upstream can make
// further changes to it.
product.setLocked(true);
ProductData existingProduct = productMap.get(product.getId());
if (existingProduct != null && !existingProduct.equals(product)) {
log.warn("Multiple versions of the same product received during dev pool resolution; " + "discarding duplicate: {} => {}, {}", product.getId(), existingProduct, product);
} else {
productMap.put(product.getId(), product);
Collection<ProductContentData> pcdCollection = product.getProductContent();
if (pcdCollection != null) {
for (ProductContentData pcd : pcdCollection) {
if (pcd == null) {
log.error("product contains a null product-content mapping: {}", product);
throw new IllegalStateException("product contains a null product-content mapping: " + product);
}
ContentData content = pcd.getContent();
// population validation for us.
if (content == null || content.getId() == null) {
log.error("product contains a null or incomplete product-content mapping: {}", product);
throw new IllegalStateException("product contains a null or incomplete " + "product-content mapping: " + product);
}
// We need to lock the incoming content here, but doing so will affect
// the equality comparison for products. We'll correct them later.
ContentData existingContent = contentMap.get(content.getId());
if (existingContent != null && !existingContent.equals(content)) {
log.warn("Multiple versions of the same content received during dev pool " + "resolution; discarding duplicate: {} => {}, {}", content.getId(), existingContent, content);
} else {
contentMap.put(content.getId(), content);
}
}
}
}
}
log.debug("Importing {} content...", contentMap.size());
for (ContentData cdata : contentMap.values()) {
cdata.setLocked(true);
}
Map<String, Content> importedContent = this.contentManager.importContent(owner, contentMap, productMap.keySet()).getImportedEntities();
log.debug("Importing {} product(s)...", productMap.size());
Map<String, Product> importedProducts = this.productManager.importProducts(owner, productMap, importedContent).getImportedEntities();
log.debug("Resolved {} dev product(s) for sku: {}", productMap.size(), sku);
return new DeveloperProducts(sku, importedProducts);
}
Aggregations