use of co.cask.cdap.api.artifact.ArtifactRange in project cdap by caskdata.
the class ArtifactClientTestRun method testNotFound.
@Test
public void testNotFound() throws Exception {
ArtifactId ghostId = NamespaceId.DEFAULT.artifact("ghost", "1.0.0");
try {
artifactClient.list(new NamespaceId("ghost"));
Assert.fail();
} catch (NotFoundException e) {
// expected
}
try {
artifactClient.getArtifactInfo(ghostId);
Assert.fail();
} catch (ArtifactNotFoundException e) {
// expected
}
try {
artifactClient.listVersions(ghostId.getParent(), ghostId.getArtifact());
Assert.fail();
} catch (ArtifactNotFoundException e) {
// expected
}
// test adding an artifact that extends a non-existent artifact
Set<ArtifactRange> parents = Sets.newHashSet(new ArtifactRange(ghostId.getParent().getNamespace(), ghostId.getArtifact(), new ArtifactVersion("1"), new ArtifactVersion("2")));
try {
artifactClient.add(NamespaceId.DEFAULT, "abc", DUMMY_SUPPLIER, "1.0.0", parents);
Assert.fail();
} catch (NotFoundException e) {
// expected
}
try {
artifactClient.getPluginTypes(ghostId);
Assert.fail();
} catch (ArtifactNotFoundException e) {
// expected
}
try {
artifactClient.getPluginSummaries(ghostId, "type");
Assert.fail();
} catch (ArtifactNotFoundException e) {
// expected
}
try {
artifactClient.getPluginInfo(ghostId, "type", "name");
Assert.fail();
} catch (NotFoundException e) {
// expected
}
}
use of co.cask.cdap.api.artifact.ArtifactRange in project cdap by caskdata.
the class ArtifactRepository method createParentClassLoader.
/**
* Create a parent classloader using an artifact from one of the artifacts in the specified parents.
*
* @param artifactId the id of the artifact to create the parent classloader for
* @param parentArtifacts the ranges of parents to create the classloader from
* @return a classloader based off a parent artifact
* @throws ArtifactRangeNotFoundException if none of the parents could be found
* @throws InvalidArtifactException if one of the parents also has parents
* @throws IOException if there was some error reading from the store
*/
private CloseableClassLoader createParentClassLoader(Id.Artifact artifactId, Set<ArtifactRange> parentArtifacts, EntityImpersonator entityImpersonator) throws ArtifactRangeNotFoundException, IOException, InvalidArtifactException {
List<ArtifactDetail> parents = new ArrayList<>();
for (ArtifactRange parentRange : parentArtifacts) {
parents.addAll(artifactStore.getArtifacts(parentRange, Integer.MAX_VALUE, ArtifactSortOrder.UNORDERED));
}
if (parents.isEmpty()) {
throw new ArtifactRangeNotFoundException(String.format("Artifact %s extends artifacts '%s' that do not exist", artifactId, Joiner.on('/').join(parentArtifacts)));
}
// check if any of the parents also have parents, which is not allowed. This is to simplify things
// so that we don't have to chain a bunch of classloaders, and also to keep it simple for users to avoid
// complicated dependency trees that are hard to manage.
boolean isInvalid = false;
StringBuilder errMsg = new StringBuilder("Invalid artifact '").append(artifactId).append("'.").append(" Artifact parents cannot have parents.");
for (ArtifactDetail parent : parents) {
Set<ArtifactRange> grandparents = parent.getMeta().getUsableBy();
if (!grandparents.isEmpty()) {
isInvalid = true;
errMsg.append(" Parent '").append(parent.getDescriptor().getArtifactId().getName()).append("-").append(parent.getDescriptor().getArtifactId().getVersion().getVersion()).append("' has parents.");
}
}
if (isInvalid) {
throw new InvalidArtifactException(errMsg.toString());
}
// assumes any of the parents will do
Location parentLocation = parents.get(0).getDescriptor().getLocation();
return createArtifactClassLoader(parentLocation, entityImpersonator);
}
use of co.cask.cdap.api.artifact.ArtifactRange in project cdap by caskdata.
the class ArtifactHttpHandlerTest method testSystemArtifactIsolation.
/**
* Tests that system artifacts can be accessed in a user namespace only if appropriately scoped.
*
* @throws Exception
*/
@Test
public void testSystemArtifactIsolation() throws Exception {
// add the app in the default namespace
File systemArtifact = buildAppArtifact(WordCountApp.class, "wordcount-1.0.0.jar");
Id.Artifact defaultId = Id.Artifact.from(Id.Namespace.DEFAULT, "wordcount", "1.0.0");
// add a system artifact. currently can't do this through the rest api (by design)
// so bypass it and use the repository directly
Id.Artifact systemId = Id.Artifact.from(Id.Namespace.SYSTEM, "wordcount", "1.0.0");
artifactRepository.addArtifact(systemId, systemArtifact, new HashSet<ArtifactRange>());
// test get /artifacts
Set<ArtifactSummary> expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
Set<ArtifactSummary> actualArtifacts = getArtifacts(Id.Namespace.DEFAULT);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts?scope=system
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, ArtifactScope.SYSTEM);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts?scope=user
expectedArtifacts = Sets.newHashSet();
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, ArtifactScope.USER);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount?scope=user
expectedArtifacts = null;
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, "wordcount", ArtifactScope.USER);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount?scope=system
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, "wordcount", ArtifactScope.SYSTEM);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount/versions/1.0.0?scope=user
ArtifactInfo actualInfo = getArtifact(defaultId, ArtifactScope.USER);
Assert.assertEquals(null, actualInfo);
// test get /artifacts/wordcount/versions/1.0.0?scope=system
actualInfo = getArtifact(defaultId, ArtifactScope.SYSTEM);
Assert.assertEquals("wordcount", actualInfo.getName());
Assert.assertEquals("1.0.0", actualInfo.getVersion());
// test delete /default/artifacts/wordcount/versions/1.0.0
deleteArtifact(defaultId, 404);
// test delete /system/artifacts/wordcount/versions/1.0.0
deleteArtifact(systemId, 200);
}
use of co.cask.cdap.api.artifact.ArtifactRange in project cdap by caskdata.
the class ArtifactHttpHandlerTest method testSystemArtifacts.
@Test
public void testSystemArtifacts() throws Exception {
// add the app in the default namespace
File systemArtifact = buildAppArtifact(WordCountApp.class, "wordcount-1.0.0.jar");
Id.Artifact defaultId = Id.Artifact.from(Id.Namespace.DEFAULT, "wordcount", "1.0.0");
Assert.assertEquals(HttpResponseStatus.OK.getCode(), addArtifact(defaultId, Files.newInputStreamSupplier(systemArtifact), null).getStatusLine().getStatusCode());
// add a system artifact. currently can't do this through the rest api (by design)
// so bypass it and use the repository directly
Id.Artifact systemId = Id.Artifact.from(Id.Namespace.SYSTEM, "wordcount", "1.0.0");
artifactRepository.addArtifact(systemId, systemArtifact, new HashSet<ArtifactRange>());
// test get /artifacts
Set<ArtifactSummary> expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.USER), new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
Set<ArtifactSummary> actualArtifacts = getArtifacts(Id.Namespace.DEFAULT);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts?scope=system
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, ArtifactScope.SYSTEM);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts?scope=user
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.USER));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, ArtifactScope.USER);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount?scope=user
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.USER));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, "wordcount", ArtifactScope.USER);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount?scope=system
expectedArtifacts = Sets.newHashSet(new ArtifactSummary("wordcount", "1.0.0", ArtifactScope.SYSTEM));
actualArtifacts = getArtifacts(Id.Namespace.DEFAULT, "wordcount", ArtifactScope.SYSTEM);
Assert.assertEquals(expectedArtifacts, actualArtifacts);
// test get /artifacts/wordcount/versions/1.0.0?scope=user
ArtifactInfo actualInfo = getArtifact(defaultId, ArtifactScope.USER);
Assert.assertEquals("wordcount", actualInfo.getName());
Assert.assertEquals("1.0.0", actualInfo.getVersion());
// test get /artifacts/wordcount/versions/1.0.0?scope=system
actualInfo = getArtifact(defaultId, ArtifactScope.SYSTEM);
Assert.assertEquals("wordcount", actualInfo.getName());
Assert.assertEquals("1.0.0", actualInfo.getVersion());
}
use of co.cask.cdap.api.artifact.ArtifactRange in project cdap by caskdata.
the class ArtifactHttpHandlerTest method invalidInputsToPluginEndpoint.
@Test
public void invalidInputsToPluginEndpoint() throws Exception {
// add an app for plugins to extend
Id.Artifact wordCount1Id = Id.Artifact.from(Id.Namespace.DEFAULT, "wordcount", "1.0.0");
Assert.assertEquals(HttpResponseStatus.OK.getCode(), addAppArtifact(wordCount1Id, WordCountApp.class).getStatusLine().getStatusCode());
// test plugin with endpoint that throws IllegalArgumentException
Manifest manifest = new Manifest();
manifest.getMainAttributes().put(ManifestFields.EXPORT_PACKAGE, PluginWithPojo.class.getPackage().getName());
Id.Artifact pluginsId = Id.Artifact.from(Id.Namespace.DEFAULT, "aggregator", "1.0.0");
Set<ArtifactRange> plugins5Parents = Sets.newHashSet(new ArtifactRange(NamespaceId.DEFAULT.getNamespace(), "wordcount", new ArtifactVersion("1.0.0"), new ArtifactVersion("2.0.0")));
Assert.assertEquals(HttpResponseStatus.OK.getCode(), addPluginArtifact(pluginsId, PluginWithPojo.class, manifest, plugins5Parents).getStatusLine().getStatusCode());
// this call should throw IllegalArgumentException
String response = callPluginMethod(pluginsId, "interactive", "aggregator", "throwException", "testString", ArtifactScope.USER, 400).getResponseBodyAsString();
Assert.assertEquals("Invalid user inputs: testString", response);
}
Aggregations