001/* 002 * The contents of this file are subject to the license and copyright 003 * detailed in the LICENSE and NOTICE files at the root of the source 004 * tree. 005 */ 006package org.fcrepo.kernel.impl.models; 007 008import org.apache.jena.graph.Node; 009import org.apache.jena.graph.Triple; 010import org.fcrepo.kernel.api.RdfStream; 011import org.fcrepo.kernel.api.Transaction; 012import org.fcrepo.kernel.api.cache.UserTypesCache; 013import org.fcrepo.kernel.api.exception.PathNotFoundException; 014import org.fcrepo.kernel.api.exception.PathNotFoundRuntimeException; 015import org.fcrepo.kernel.api.identifiers.FedoraId; 016import org.fcrepo.kernel.api.models.FedoraResource; 017import org.fcrepo.kernel.api.models.NonRdfSourceDescription; 018import org.fcrepo.kernel.api.models.ResourceFactory; 019import org.fcrepo.kernel.api.rdf.DefaultRdfStream; 020import org.fcrepo.persistence.api.PersistentStorageSessionManager; 021 022import java.net.URI; 023import java.util.List; 024import java.util.stream.Stream; 025 026import static org.apache.jena.graph.NodeFactory.createURI; 027import static org.fcrepo.kernel.api.RdfLexicon.RDF_SOURCE; 028 029/** 030 * Implementation of a non-rdf source description 031 * 032 * @author bbpennel 033 */ 034public class NonRdfSourceDescriptionImpl extends FedoraResourceImpl implements NonRdfSourceDescription { 035 036 private static final URI RDF_SOURCE_URI = URI.create(RDF_SOURCE.getURI()); 037 038 /** 039 * Construct a description resource 040 * 041 * @param fedoraID internal identifier 042 * @param transaction transaction 043 * @param pSessionManager session manager 044 * @param resourceFactory resource factory 045 * @param userTypesCache the user types cache 046 */ 047 public NonRdfSourceDescriptionImpl(final FedoraId fedoraID, 048 final Transaction transaction, 049 final PersistentStorageSessionManager pSessionManager, 050 final ResourceFactory resourceFactory, 051 final UserTypesCache userTypesCache) { 052 super(fedoraID, transaction, pSessionManager, resourceFactory, userTypesCache); 053 } 054 055 @Override 056 public String getId() { 057 return getFedoraId().getResourceId(); 058 } 059 060 @Override 061 public FedoraResource getDescribedResource() { 062 // Get a FedoraId for the binary 063 FedoraId describedId = getFedoraId().asBaseId(); 064 if (getFedoraId().isMemento()) { 065 describedId = describedId.asMemento(getFedoraId().getMementoInstant()); 066 } 067 try { 068 return this.resourceFactory.getResource(transaction, describedId); 069 } catch (final PathNotFoundException e) { 070 throw new PathNotFoundRuntimeException(e.getMessage(), e); 071 } 072 } 073 074 @Override 075 public List<URI> getSystemTypes(final boolean forRdf) { 076 var types = resolveSystemTypes(forRdf); 077 078 if (types == null) { 079 types = super.getSystemTypes(forRdf); 080 // NonRdfSource gets the ldp:Resource and adds ldp:RDFSource types. 081 types.add(RDF_SOURCE_URI); 082 } 083 084 return types; 085 } 086 087 @Override 088 public RdfStream getTriples() { 089 // Remap the subject to the described resource 090 // TODO: With FCREPO-3819 and FCREPO-3820, this will no longer be necessary. 091 // But existing sites might have RDF with NonRdfSourceDescription subjects, so leave it for now. 092 final Node describedID = createURI(this.getDescribedResource().getId()); 093 final Stream<Triple> triples = super.getTriples().map(t -> { 094 if (t.getSubject().hasURI(this.getId())) { 095 return new Triple(describedID, t.getPredicate(), t.getObject()); 096 } else { 097 return t; 098 } 099 }); 100 return new DefaultRdfStream(describedID, triples); 101 } 102}