Skip to main content

Migrate to 5.11

Spring

Spring was updated to version 2.6. As a result of the necessary configuration changes, the class com.activeviam.cfg.SpringRestServiceInitializer must be added to your Spring configuration, unless you already import com.qfs.server.cfg.impl.ActiveViamRestServicesConfig or com.qfs.content.cfg.impl.StandaloneContentServerRestConfig to configure the REST services.

Copper

The performances of the calculations defined in Copper have been improved. The transient memory generated at query time will be reduced by limiting the boxing phenomenon. (The use, for instance, of java.lang.Integer instead of int)

As a consequence, multiple methods are now deprecated. We strongly advise users to migrate out of any deprecated methods, as these changes are strictly brought to users for transient memory performance purposes.

  • Combining multiple CopperElements through Copper.combine(...) to create a new measure is no longer done with CopperMeasure map(SerializableFunction<IRecordReader, Object> mapper). The method is now called mapToObject to follow the changes brought to other methods. For instance,

    Copper.combine(Copper.sum(RISK__PNL), Copper.member(City))
    .mapToInt(reader -> {
    if (reader.read(1).equals("NYC") {
    return 0;
    } else {
    return reader.readDouble(0) > 0 ? 1 : -1;
    }
    })
  • Combining multiple CopperMeasure through Copper.combine(...) to create a new measure is no longer done with CopperMeasure map(SerializableFunction<IRecordReader, Object> mapper). Instead, the new method's output type will dictate the method that should be used. For instance, if these measures are combined into a measure that outputs int, one should use CopperMeasure mapToInt(SerializableToIntFunction<IArrayReader> mapper). For instance,

    Copper.combine(Copper.sum(RISK__PNL), Copper.constant(0d).withName(PNL_LIMIT))
    .mapToInt(a -> a.readDouble(0) >= a.readDouble(1) ? 1 : -1)
  • Modifying a measure follows the same rule : Copper.sum(RISK__PNL).mapToDouble(reader -> reader.readDouble(0) * 2d)

  • The aforementioned changes make CopperMeasure#withType() relatively redundant: it is removed for measures that have already specified it through the choice of mapping method.

  • Contrary to the specialized implementations like mapToInt(SerializableToIntFunction<IArrayReader>), mapToDouble(SerializableToDoubleFunction<IArrayReader>, etc... The method mapToObject takes as argument a SerializableBiConsumer<IArrayReader, IWritableCell>. The provided cell must be used to write the result:

    Copper.sum(RISK__PNL).mapToObject((reader, cell) -> {
    if (reader.readDouble(0) <= 1) {
    cell.writeDouble(reader.readDouble(0));
    }
    });
  • From now on, only two types of measures support setting a specific output type: when using the various mapToDouble/mapToLong methods and the new map, or right after a plus/minus/etc. using withType.

Post Processors

To also reduce the memory consumption of IPostProcessors and IEvaluators, we added new implementations of these components.

AAdvancedPostProcessor<outputType> becomes AAdvancedPostProcessorV2 and does not declare a generic output type. All Post Processors must now receive the property outputType in their initialization properties.

  • IEvaluatorV2's evaluation method is void evaluate(ILocation location, IRecordReader aggregatedMeasures, IWritableCell resultCell). Instead of reading underlying values from an Object[], one now needs to read them from the given IRecordReader, using the appropriate specialized method, and write the result of the evaluation into the resultCell. For instance,

    @Override
    public Double evaluate(ILocation location, Object[] measures) {
    if (measures[0] == null) {
    return null;
    } else {
    return 10D + ((Number) measures[0]).doubleValue();
    }
    }

    becomes

    @Override
    public void evaluate(ILocation location, IRecordReader aggregatedMeasures, IWritableCell resultCell) {
    if (!aggregatedMeasures.isNull(0)) {
    resultCell.writeDouble(10D + aggregatedMeasures.readDouble(0));
    }
    }
  • In a similar fashion, all abstract implementations of ITransformProcedure are now deprecated. It is now necessary to directly implement the interface. As before, one can now either implement the method transform or the method doTransform, depending on the expected behavior.

  • Similarly, the method evaluateLeaf of the ADynamicAggregationPostProcessor was reworked to provide a cell in ADynamicAggregationPostProcessorV2

  • The method IPostProcessor#init(Properties) has been completely reworked, with clear methods to implement or override for each of the most important parts of the post processor.

Distribution

Now, cubes within a distributed cluster have a unique identifier that will be used to expose their remote addresses through the query cube they are related to. This introduces a breaking change in the distributed messenger constructors: ADistributedMessenger now include CubeEndPointInfo in its constructor, a data structure holding information regarding cube addresses and identifiers. These data are solely resolved by core ActivePivot, thus one has just to include the new field in any subsequent messenger.

Analysis Hierarchies

The implementations of Analysis Hierarchies have been cleaned as part of 5.11. Users are expected to extend and override AAnalysisHierarchyV2.
Most users should not see a difference because Analysis Hierarchies were mostly populated with static members.

The contract between the two classes has been better described. There is now a clear separation between static members and members generated from the ActivePivot Schema.
Static members are still created by AAnalysisHierarchyV2#buildDiscriminatorPaths.
However, to process introspected members, the new method is #processIntrospectedMember, replacing a judicious override of #contributeMember. Instead of consuming a member and having to call the super method to do the contribution, users receive the introspected members and their counts, as well a consumer function. It is up to the function to generate as many members as it wants and to pass each one of them to the consumer to publish them.

As before, AAnalysisHierarchyV2 sources are available for inspection and inspiration.

Datastore

  • To create datastore queries one should now give a SelectionField instead of a String which was the path to the field.
  • ReferencedField was renamed ReachableField.
  • ISelectionField was removed. It is replaced by SelectionField.
  • SelectionField.getName() was renamed getAlias().

getMostRecentVersion() should never be used by a project. It is an internal method. Replace all calls to getMostRecentVersion() by a call to getHead().

Vectors

All methods in IVectorBinding were changed from: void methodName(IVector source, IVector destination) to: void methodName(IVector left, IVector right)

This change is performed to align all the vector APIs together. For instance, doing vectorA.minus(vectorB) is now, under the hood, calling binding.minus(vectorA, vectorB), keeping the arguments in their initial order. This should better prevent mistakes in the implementations of methods such as IVectorBinding.applyAsDouble(left, right, DoubleBinaryOperator).

Users writing their own vector implementations and their own bindings for these vectors will probably need to ensure their bindings are in order.

Content Service UI

ContentServerResourceServerConfig is replaced by AdminUIResourceServerConfig and content-server-ui.jar is replaced by admin-ui.jar.

Content Server and ActiveMonitor Database

Migrating H2 to v2

The dependency version of h2 for ActivePivot and ActiveMonitor was upgraded from 1.4.200 to 2.1.214. This version change makes h2-generated .db files incompatible between 6.0 and the prior versions.

Unwanted .db files can simply be deleted, or restoring the entries of your current database can be attempted using the h2 migration notes.

SOAP

We no longer return a full ActivePivotManagerDescription in our webservices with retrieveManagerDescription but instead return a lighter description called SoapActivePivotDiscovery in retrieveActivePivotDiscovery. This discovery will contain all the information you previously wanted from an ActivePivotManagerDescription including a list of Catalogs and a list of Cubes (And in each cube, its measures, dimensions, hierarchies and levels).

retrieveActivePivotDescription also no longer return a IActivePivotDescription but a SoapCubeDiscovery which is a lighter description of your ActivePivot.

retrieveSchemaDescription no longer exists in our webservices.

XML

Building ActivePivot from an XML description file is no longer available. Users are invited to use our fluent builder API using StartBuilding.

ActiveviamProperties

The options for the ActiveViam Property -Dactiveviam.chunkAllocatorClass were moved to specialized packages. See the Javadoc of the property CHUNK_ALLOCATOR_CLASS_PROPERTY.