Project

Profile

Help

Story #3295

Updated by amacdona@redhat.com almost 7 years ago

Tasks that create new Publications have to write to pulpcore tables in transactions, mark the publication complete, and clean up the database if the task fails. All of this should be handled by a context manager that is a part of the plugin API. 


 h2. Proposal: Wrapper for the Publication object in the plugin API 

 The pulpcore model for Publication will be removed from the plugin API, so the wrapper will be the only supported way for plugin writers to create new Publications, and must be performed only in celery tasks.  

 The Publication wrapper:  
 * can be used as a context manager that creates Publications.  
 * Publications accept a RepositoryVersion facade/wrapper 
 * uses transactions to create a new publication and update related tables 
 * handles failure scenarios by cleaning up incomplete work 
 * can be used to retrieve content from a Publication.repository_version.content() 
 * can create new PublishedMetadata objects from files 
 * can create new PublishedArtifacts from content_artifacts Artifacts or RemoteArtifacts 
 * Can only add publish Metadata and Artifacts if complete=False 
 * Can only add Metadata and Artifacts publish if run in a task 
 * has exclusive control of the Publication.complete flag 


 h3. example usage 

 Create a new Publication. Plugin writers can use this object to create and write metadata, and can be used to create PublishedMetadata. 

 <pre><code class="python"> 

 with Publication.create(repository_version) as publication: 
     # If Publication requires new metadata, generate and write it. 
     metadata_path = some_function_to_write_metadata(publication) 
     # Safely Create and save PublishedMetadata object 
     publication.add_metadata(metadata_path) publication.publish_metadata(metadata_path) 
     # Safely create Create and save PublishedArtifact  
     publication.add_artifact(artifact) publication.publish_artifact(artifact) 


 </code></pre> 


 The wrapper object can also be used to access the Publication model layer, which replaces the use of plugin.models.Publication.objects.get() with: 

 <pre><code class="python"> 

 latest_publication = Publication.latest(repository) 
 # repository_version is a RepositoryVersion wrapper from #3285 
 some_publication = Publication.get(repository_version=repository_version) 


 </code></pre> 

 Note: 
 Since the Publication accepts a RepositoryVersion facade (https://pulp.plan.io/issues/3285), it will need to use `RepositoryVersion._model`. `_model` for content in publication.content() 
     # This is an protected method to prevent plugin use. Since we need the model here, we have to fudge the rules a little bit here to keep the Plugin API clean. Please include this in a comment. shortcut for publication._model.repository_version.content() 
     do_something(content) 

 </code></pre> 

Back