1 package com.atlassian.plugins.rest.module;
2
3 import java.util.Collections;
4 import java.util.Set;
5
6 import com.atlassian.plugin.module.ContainerManagedPlugin;
7 import com.google.common.base.Preconditions;
8 import com.google.common.collect.ImmutableSet;
9 import com.sun.jersey.api.core.ResourceConfig;
10 import com.sun.jersey.core.spi.component.ComponentContext;
11 import com.sun.jersey.core.spi.component.ComponentScope;
12 import com.sun.jersey.core.spi.component.ioc.IoCComponentProvider;
13 import com.sun.jersey.core.spi.component.ioc.IoCComponentProviderFactory;
14 import com.sun.jersey.core.spi.component.ioc.IoCManagedComponentProvider;
15 import com.sun.jersey.server.impl.container.servlet.JSPTemplateProcessor;
16 import com.sun.jersey.spi.resource.PerRequest;
17
18 import static com.google.common.collect.Sets.difference;
19
20
21
22
23
24 public class OsgiComponentProviderFactory implements IoCComponentProviderFactory {
25
26 private static final Set<Class<?>> EXCLUDE = ImmutableSet.<Class<?>>of(JSPTemplateProcessor.class);
27
28
29
30
31 private final ContainerManagedPlugin plugin;
32
33
34
35
36 private final Set<Class<?>> classes;
37
38 private final Set<?> instances;
39
40 public OsgiComponentProviderFactory(ResourceConfig resourceConfig, ContainerManagedPlugin plugin) {
41 this.plugin = Preconditions.checkNotNull(plugin);
42
43
44 final Set<Class<?>> classes = Preconditions.checkNotNull(resourceConfig).getClasses();
45 if (classes != null) {
46 this.classes = difference(ImmutableSet.copyOf(classes), EXCLUDE);
47 } else {
48 this.classes = Collections.emptySet();
49 }
50
51 if (resourceConfig instanceof OsgiResourceConfig) {
52 instances = ((OsgiResourceConfig) resourceConfig).getInstances();
53 } else {
54 instances = Collections.emptySet();
55 }
56 }
57
58 public IoCComponentProvider getComponentProvider(final Class<?> c) {
59 return getComponentProvider(null, c);
60 }
61
62 public IoCComponentProvider getComponentProvider(ComponentContext cc, Class<?> c) {
63 if (!classes.contains(c)) {
64 return null;
65 }
66 final Object instance = getInstance(c);
67 return instance == null ? new ContainerManagedComponentProvider(plugin, c) : new InstanceOsgiComponentProvider(instance);
68 }
69
70 private Object getInstance(Class<?> c) {
71 for (Object o : instances) {
72 if (o.getClass().equals(c)) {
73 return o;
74 }
75 }
76 return null;
77 }
78
79 private static class ContainerManagedComponentProvider implements IoCManagedComponentProvider {
80 private final ContainerManagedPlugin plugin;
81 private final Class<?> componentClass;
82
83 public ContainerManagedComponentProvider(ContainerManagedPlugin plugin, Class<?> componentClass) {
84 this.plugin = plugin;
85 this.componentClass = componentClass;
86 }
87
88 public Object getInstance() {
89 return plugin.getContainerAccessor().createBean(componentClass);
90 }
91
92 public ComponentScope getScope() {
93
94
95 if (componentClass.getAnnotation(PerRequest.class) != null) {
96 return ComponentScope.PerRequest;
97 }
98 return ComponentScope.Singleton;
99 }
100
101 public Object getInjectableInstance(Object o) {
102 plugin.getContainerAccessor().injectBean(o);
103 return o;
104 }
105 }
106
107 private static class InstanceOsgiComponentProvider implements IoCManagedComponentProvider {
108 private final Object instance;
109
110 public InstanceOsgiComponentProvider(Object instance) {
111 this.instance = Preconditions.checkNotNull(instance);
112 }
113
114 public ComponentScope getScope() {
115 return ComponentScope.Singleton;
116 }
117
118 public Object getInstance() {
119 return instance;
120 }
121
122 public Object getInjectableInstance(Object o) {
123 return o;
124 }
125 }
126 }