XAP

The Space Interface

A Space is a logical in-memory service, which can store entries of information. An entry is a domain object. In Java, an entry can be a simple POJO, or a SpaceDocument.

When a client connects to a Space, a proxy is created that holds a connection, which implements the space API. All client interaction is performed through this proxy.

The Space is accessed via a programmatic interface that supports the following main functions:

  • Write - the semantics of writing a new entry of information to the Space.
  • Read - read the contents of a stored entry into the client side.
  • Take - get the value from the Space and delete its content.
  • Notify - alert when the contents of an entry of interest have registered changes.

For more information about Spaces, see the Operations page.

Embedded Space

A client communicating with a an embedded Space performs all its operations via local connection. There is no network overhead when using this approach.

The following is an example of how to create an embedded Space. The EmbeddedSpaceConfigurer is used to configure the Space URL:

GigaSpace gigaSpace = new GigaSpaceConfigurer(new EmbeddedSpaceConfigurer("mySpace")).gigaSpace();
<os-core:embedded-space id="space" space-name="mySpace"/>
<os-core:giga-space id="gigaSpace" space="space"/>
<bean id="space" class="org.openspaces.core.space.EmbeddedSpaceFactoryBean">
    <property name="name" value="space" />
</bean>

<bean id="gigaSpace" class="org.openspaces.core.GigaSpaceFactoryBean">
    <property name="space" ref="space" />
</bean>

Instead of defining everything inside the PU,xml, it is also possible to configure the PU via code and then it is only required to specify the class that implements the configuration. You can find an example in the built-in blueprint (stateful) by selecting option 2 from the blueprint generation as shown on this Blueprints page.

The Embedded space can be used in a distributed architecture such as the replicated or partitioned clustered space:

A simple way to use the embedded Space in a clustered architecture is by deploying a clustered Space, or packaging your application as a Processing Unit and deploying it using the relevant SLA.

Remote Space

A client communicating with a remote Space performs all its operations via a remote connection. The remote Space can be partitioned (with or without backups) or replicated (based on synchronous or asynchronous replication).

The following is an example of how a client application can create a proxy for interacting with a remote Space:

GigaSpace gigaSpace = new GigaSpaceConfigurer(new SpaceProxyConfigurer("mySpace")).gigaSpace();
<os-core:space-proxy  id="space" space-name="mySpace"/>
<os-core:giga-space id="gigaSpace" space="space"/>
<bean id="space" class="org.openspaces.core.space.SpaceProxyFactoryBean">
    <property name="name" value="space" />
</bean>

<bean id="gigaSpace" class="org.openspaces.core.GigaSpaceFactoryBean">
    <property name="space" ref="space" />
</bean>

Instead of defining everything inside the PU.xml, it is also possible to configure the PU via code and then it is only required to specify the class that implements the configuration. You can find an example in the built-in blueprint for remote proxy (stateless) by selecting option 4 from the blueprint generation as shown on this Blueprints page.

For more information about the Space URL Properties, see The Space URL.

Reconnection

When working with a remote Space, the Space may become unavailable (due to network problems, Processing Unit relocation, etc.). For information on how such disruptions are handled and configured, refer to Proxy Connectivity.

Local Cache

GigaSpaces supports a local cache (near cache) configuration. This provides a front-end, client-side cache that is used with the read operations implicitly. The local cache is loaded on demand or when you perform a read operation, and is updated implicitly by the Space.

The following is an example of a GigaSpace construct with a local cache:

// Initialize remote space configurer:
SpaceProxyConfigurer urlConfigurer = new SpaceProxyConfigurer("space");
// Initialize local cache configurer
LocalCacheSpaceConfigurer localCacheConfigurer = new LocalCacheSpaceConfigurer(urlConfigurer);

// Create local cache:
GigaSpace localCache = new GigaSpaceConfigurer(localCacheConfigurer).gigaSpace();
<os-core:space-proxy  id="space" space-name="mySpace"/>
<os-core:local-cache id="localCacheSpace" space="space"/>
<os-core:giga-space id="localCache" space="localCacheSpace"/>
<bean id="space" class="org.openspaces.core.space.SpaceProxyFactoryBean">
    <property name="name" value="space" />
</bean>

<bean id="localCacheSpace"
    class="org.openspaces.core.space.cache.LocalCacheSpaceFactoryBean">
    <property name="space" ref="space" />
</bean>

Local View

GigaSpaces supports a local view configuration. This provides a front-end, client-side cache that is used with any read or readMultiple operations implicitly. The local view is loaded on start, and is updated implicitly by the Space.

Here is an example for a GigaSpace construct with a local cache:

// Initialize remote space configurer:
SpaceProxyConfigurer configurer = new SpaceProxyConfigurer("space");

// Initialize local view configurer
LocalViewSpaceConfigurer localViewConfigurer = new LocalViewSpaceConfigurer(configurer)
            .addViewQuery(new SQLQuery<Message>(Message.class, "processed = true"))
            .addViewQuery(new SQLQuery<Message>(Message.class, "priority > 3"));

// Create local view:
GigaSpace localView = new GigaSpaceConfigurer(localViewConfigurer).gigaSpace();
<os-core:space-proxy id="space" space-name="mySpace" />

<os-core:local-view id="localViewSpace" space="space">
    <os-core:view-query class="Message" where="processed = true"/>
    <os-core:view-query class="Message" where="priority > 3"/>
</os-core:local-view>

<os-core:giga-space id="localView" space="localViewSpace"/>
<bean id="space" class="org.openspaces.core.space.SpaceProxyFactoryBean">
    <property name="name" value="space" />
</bean>

<bean id="viewSpace" class="org.openspaces.core.space.cache.LocalViewSpaceFactoryBean">
    <property name="space" ref="space" />
    <property name="localViews">
        <list>
            <bean class="com.j_spaces.core.client.view.View">
                <constructor-arg index="0" value="com.example.Message1" />
                <constructor-arg index="1" value="processed = true" />
            </bean>
            <bean class="com.j_spaces.core.client.view.View">
                <constructor-arg index="0" value="com.example.Message2" />
                <constructor-arg index="1" value="priority > 3" />
            </bean>
        </list>
    </property>
</bean>

Resource Cleanup

There are two types of resources associated with Space instances and Space clients that have to be released before shutting down your application.

Thread and Memory Resources

If your Space client or embedded Space are running within a Spring-enabled environment (such as the GigaSpaces service grid or a standalone Spring application), and are configured in a Spring application context, these resources will be cleaned up automatically when the Spring application context is destroyed. However, if you start the Space client or Space instance programmatically, you must call the SpaceConfigurer close() method when your application no longer uses the Space instance/Space client.

Example:

SpaceProxyConfigurer spaceProxyConfigurer = new SpaceProxyConfigurer("space");
 //....
spaceProxyConfigurer.close();

// Local cache
LocalCacheSpaceConfigurer localCacheConfigurer = new LocalCacheSpaceConfigurer(urlConfigurer);
localCacheConfigurer.close();

// Local view
LocalViewSpaceConfigurer localViewConfigurer = new LocalViewSpaceConfigurer(urlConfigurer);
localViewConfigurer.close();

When using LocalCache and LocalView. you need to call the close() method on their respective configurer.

Communication Resources

All communication-related resources in GigaSpaces are shared between all the GigaSpaces components at the Java classloader level. If you're using the GigaSpaces service grid to run your GigaSpaces application, you do not need to handle the cleanup of communication resources explicitly.

If your application runs in a standalone environment or another hosted environment (such as a JEE application server), you must explicitly clean up those resources. You have to shut down these resources explicitly when your application no longer uses the GigaSpaces components (for example, when it is undeployed from the application server). This is done by calling the static shutdown() method on the LRMIManager.

If the JVM process is shut down anyway, you don't have to explicitly shut down the communication resources.

Example:

SpaceProxyConfigurer spaceProxyConfigurer = new SpaceProxyConfigurer("space");
 //....
spaeProxyConfigurer.close();

LRMIManager.shutdown();

Security

A secured Space should be configured with a security context so that it can be accessed (when connecting to it remotely). The following is an example of how this can be configured:

<os-core:space-proxy id="space" space-name="mySpace">
    <os-core:security username="sa" password="adaw@##$" />
</os-core:space-proxy>
<bean id="space" class="org.openspaces.core.space.SpaceProxyFactoryBean">
    <property name="name" value="space" />
    <property name="securityConfig">
        <bean class="org.openspaces.core.space.SecurityConfig">
            <property name="username" value="sa" />
            <property name="password" value="adaw@##$" />
        </bean>
    </property>
</bean>

The following is an example of how to define security with an embedded Space. In this case, we enable security and specify the username and password.

<os-core:space-proxy  id="space" space-name="mySpace">
    <os-core:security username="sa" password="adaw@##$" />
</os-core:space-proxy>
<bean id="space" class="org.openspaces.core.space.EmbeddedSpaceFactoryBean">
    <property name="name" value="space" />
    <property name="securityConfig">
        <bean class="org.openspaces.core.space.SecurityConfig">
            <property name="username" value="sa" />
            <property name="password" value="adaw@##$" />
        </bean>
    </property>
</bean>

You can configure the Space to be secured using deploy-time properties (bean-level properties), without declaring the security element. The security.username and security.password can be provided, and the Spaces defined within the Processing Unit are automatically secured.

For more information about how to secure GigaSpaces components, refer to the Security section of the Administrator guide.

Persistency

When constructing a Space, you can provide Space Persistency extensions using Spring-based configuration instead of using the Space schema. The following is an example of how it can be defined:

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
    <property name="driverClassName" value="org.hsqldb.jdbcDriver"/>
    <property name="url" value="jdbc:hsqldb:hsql://localhost:9001"/>
    <property name="username" value="sa"/>
    <property name="password" value=""/>
</bean>

<bean id="sessionFactory" class="org.springframework.orm.hibernate16.2.1.LocalSessionFactoryBean">
    <property name="dataSource" ref="dataSource"/>
    <property name="mappingResources">
        <list>
            <value>Person.hbm.xml</value>
        </list>
    </property>
    <property name="hibernateProperties">
        <props>
            <prop key="hibernate.dialect">org.hibernate.dialect.HSQLDialect</prop>
            <prop key="hibernate.cache.provider_class">org.hibernate.cache.NoCacheProvider</prop>
            <prop key="hibernate.cache.use_second_level_cache">false</prop>
            <prop key="hibernate.cache.use_query_cache">false</prop>
            <prop key="hibernate.hbm2ddl.auto">update</prop>
        </props>
    </property>
</bean>

<bean id="hibernateSpaceDataSource" class="com.gigaspaces.datasource.hibernate.DefaultHibernateSpaceDataSource">
    <property name="sessionFactory" ref="sessionFactory"/>
</bean>

<os-core:embedded-space id="space" space-name="mySpace" schema="persistent" space-data-source="hibernateSpaceDataSource" />
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
    <property name="driverClassName" value="org.hsqldb.jdbcDriver"/>
    <property name="url" value="jdbc:hsqldb:hsql://localhost:9001"/>
    <property name="username" value="sa"/>
    <property name="password" value=""/>
</bean>

<bean id="sessionFactory" class="org.springframework.orm.hibernate16.2.1.LocalSessionFactoryBean">
    <property name="dataSource" ref="dataSource"/>
    <property name="mappingResources">
        <list>
            <value>Person.hbm.xml</value>
        </list>
    </property>
    <property name="hibernateProperties">

        <props>
            <prop key="hibernate.dialect">org.hibernate.dialect.HSQLDialect</prop>
            <prop key="hibernate.cache.provider_class">org.hibernate.cache.NoCacheProvider</prop>
            <prop key="hibernate.cache.use_second_level_cache">false</prop>
            <prop key="hibernate.cache.use_query_cache">false</prop>
            <prop key="hibernate.hbm2ddl.auto">update</prop>
        </props>
    </property>
</bean>

<bean id="hibernateSpaceDataSource" class="com.gigaspaces.datasource.hibernate.DefaultHibernateSpaceDataSource">
    <property name="sessionFactory" ref="sessionFactory"/>
</bean>

<bean id="space" class="org.openspaces.core.space.EmbeddedSpaceFactoryBean">
    <property name="name" value="space" />
    <property name="schema" value="persistent" />
    <property name="spaceDataSource" ref="hibernateSpaceDataSource" />
</bean>

The above example uses Spring built-in support for configuring both a custom JDBC DataSource and a Hibernate SessionFactory to define and use the GigaSpaces built-in HibernateSpaceDataSource. The GigaSpaces data source is then injected into the Space construction (note the specific schema change), and causes the Space to use it.

This configuration can also be used with the GigaSpaces Mirror Service deployed as a Processing Unit.

Additional Resources