Пример #1
0
             ITRexSpatialMemoryCacheContext[] CacheContexts) GetIntermediary(ICombinedFilter filter)
            {
                // Construct the appropriate list of surveyed surfaces
                // Obtain local reference to surveyed surface list. If it is replaced while processing the
                // list then the local reference will still be valid allowing lock free read access to the list.
                ISurveyedSurfaces filteredSurveyedSurfaces = null;
                var surveyedSurfaceList = siteModel.SurveyedSurfaces;

                if (includeSurveyedSurfaceInformation && surveyedSurfaceList?.Count > 0)
                {
                    filteredSurveyedSurfaces = DIContext.Obtain <ISurveyedSurfaces>();

                    // Filter out any surveyed surfaces which don't match current filter (if any) - realistically, this is time filters we're thinking of here
                    surveyedSurfaceList.FilterSurveyedSurfaceDetails(filter.AttributeFilter.HasTimeFilter,
                                                                     filter.AttributeFilter.StartTime, filter.AttributeFilter.EndTime,
                                                                     filter.AttributeFilter.ExcludeSurveyedSurfaces(), filteredSurveyedSurfaces,
                                                                     filter.AttributeFilter.SurveyedSurfaceExclusionList);

                    // Ensure that the filtered surveyed surfaces are in a known ordered state
                    filteredSurveyedSurfaces.SortChronologically(filter.AttributeFilter.ReturnEarliestFilteredCellPass);
                }

                var filteredSurveyedSurfacesAsArray = filteredSurveyedSurfaces?.Count > 0 ? filteredSurveyedSurfaces.Select(s => s.ID).ToArray() : new Guid[0];

                // Get a caching context for the sub grids returned by this requester, but only if the requested grid data type supports it
                ITRexSpatialMemoryCacheContext[] subGridCacheContexts = null;

                if (_enableGeneralSubGridResultCaching &&
                    ClientLeafSubGrid.SupportsAssignationFromCachedPreProcessedClientSubGrid[(int)gridDataType])
                {
                    filter.AttributeFilter.SiteModel = siteModel;
                    var contextType1 = Utilities.IntermediaryICGridDataTypeForDataType(gridDataType, true);
                    var contextType2 = Utilities.IntermediaryICGridDataTypeForDataType(gridDataType, false);

                    var context1 = SubGridCache?.LocateOrCreateContext(siteModel.ID, contextType1,
                                                                       SpatialCacheFingerprint.ConstructFingerprint(siteModel.ID, contextType1, filter, filteredSurveyedSurfacesAsArray));
                    var context2 = SubGridCache?.LocateOrCreateContext(siteModel.ID, contextType2,
                                                                       SpatialCacheFingerprint.ConstructFingerprint(siteModel.ID, contextType2, filter, filteredSurveyedSurfacesAsArray));

                    subGridCacheContexts = new[] { context1, context2 }.Where(x => x != null).ToArray();
                }

                return(gridDataType,
                       filter,
                       filteredSurveyedSurfaces,
                       _surfaceElevationPatchRequestFactory(SubGridCache, SubGridCache?.LocateOrCreateContext(siteModel.ID, GridDataType.SurveyedSurfaceHeightAndTime,
                                                                                                              SpatialCacheFingerprint.ConstructFingerprint(siteModel.ID, GridDataType.SurveyedSurfaceHeightAndTime, null,
                                                                                                                                                           filteredSurveyedSurfaces?.Select(x => x.ID).ToArray() ?? new Guid[0]))),
                       subGridCacheContexts);
            }
Пример #2
0
        public void Test_TRexSpatialMemoryCacheTests_DesignChangeInvalidation()
        {
            var projectUid   = Guid.NewGuid();
            var gridDataType = Types.GridDataType.PassCount;
            var designUid    = Guid.NewGuid();
            var designUid2   = Guid.NewGuid();

            Guid[] includedSurveyedSurfaces  = new Guid[] { designUid };
            Guid[] includedSurveyedSurfaces2 = new Guid[] { designUid2 };

            using (var cache = new TRexSpatialMemoryCache(20000, 1000000, 0.5))
            {
                // Create a context with a included design and validate that a design change causes the appropriate invalidation
                var testGuid = Guid.NewGuid();
                var context  = cache.LocateOrCreateContext(projectUid, gridDataType, SpatialCacheFingerprint.ConstructFingerprint(projectUid, gridDataType, null, includedSurveyedSurfaces));
                // this content will remain in cache as it uses a different design
                var context2 = cache.LocateOrCreateContext(projectUid, gridDataType, SpatialCacheFingerprint.ConstructFingerprint(projectUid, gridDataType, null, includedSurveyedSurfaces2));

                Assert.True(context.MarkedForRemoval == true, "Empty contents should be marked for removal");

                TRexSpatialMemoryCacheContextTests_Element[,] items  = new TRexSpatialMemoryCacheContextTests_Element[100, 100];
                TRexSpatialMemoryCacheContextTests_Element[,] items2 = new TRexSpatialMemoryCacheContextTests_Element[100, 100];

                // Add content to our 2 contexts
                for (var k = 1; k < 3; k++)
                {
                    for (var i = 0; i < 100; i++)
                    {
                        for (var j = 0; j < 100; j++)
                        {
                            if (k == 1)
                            {
                                items[i, j] = new TRexSpatialMemoryCacheContextTests_Element
                                {
                                    CacheOriginX = (int)(i * SubGridTreeConsts.SubGridTreeDimension),
                                    CacheOriginY = (int)(j * SubGridTreeConsts.SubGridTreeDimension),
                                    SizeInBytes  = 1
                                };
                                cache.Add(context, items[i, j], context.InvalidationVersion).Should().Be(CacheContextAdditionResult.Added);;
                            }
                            else
                            {
                                items2[i, j] = new TRexSpatialMemoryCacheContextTests_Element
                                {
                                    CacheOriginX = (int)(i * SubGridTreeConsts.SubGridTreeDimension),
                                    CacheOriginY = (int)(j * SubGridTreeConsts.SubGridTreeDimension),
                                    SizeInBytes  = 1
                                };
                                cache.Add(context2, items2[i, j], context2.InvalidationVersion).Should().Be(CacheContextAdditionResult.Added);
                            }
                        }
                    }
                }

                // verify items added OK
                Assert.True(context.MarkedForRemoval == false, "Context should not be marked for removal");
                Assert.True(context.TokenCount == 10000, "Token count incorrect after addition");
                Assert.True(context2.MarkedForRemoval == false, "Context2 should not be marked for removal");
                Assert.True(context2.TokenCount == 10000, "Token count incorrect after addition of context2");

                // invalidate first of the 2 contexts added
                cache.InvalidateDueToDesignChange(projectUid, designUid);

                cache.MRUList.TokenCount.Should().Be(10000);

                int counter = 0;
                for (var i = 0; i < 100; i++)
                {
                    for (var j = 0; j < 100; j++)
                    {
                        cache.MRUList.Get(counter++).Should().NotBe(items[i, j]);
                    }
                }

                for (var i = 0; i < 100; i++)
                {
                    for (var j = 0; j < 100; j++)
                    {
                        cache.MRUList.Get(counter++).Should().Be(items2[i, j]);
                    }
                }

                //Test context is removed
                Assert.True(context.MarkedForRemoval == true, "Empty context should be marked for removal");
                Assert.True(context.TokenCount == 0, "Token count incorrect after invalidation");
                // Test context2 remains
                Assert.True(context2.MarkedForRemoval == false, "Context2 should not be marked for removal");
                Assert.True(context2.TokenCount == 10000, "Token count incorrect after test");
            }
        }
Пример #3
0
 /// <summary>
 /// Computes a Fingerprint for use in caching surveyed surface height + time responses
 /// Note: This fingerprint used the SurveyedSurfaceHeightAndTime grid data type in the cache fingerprint,
 /// even though the core engine returns HeightAndTime results. This allows HeightAndTime and
 /// SurveyedSurfaceHeightAndTime results to cohabit in the same cache
 /// </summary>
 public string CacheFingerprint()
 {
     return(SpatialCacheFingerprint.ConstructFingerprint(SiteModelID, GridDataType.SurveyedSurfaceHeightAndTime, null, IncludedSurveyedSurfaces));
 }