示例#1
0
        private void AddIncludeResourceInstanceForRevIncludes(List <DtoResource> IncludeResourceList, HashSet <string> CacheResourceIDsAlreadyCollected, PyroSearchParameters SearchParameters)
        {
            //Here we need to add compartment search, if we have a Compartment and id
            IDatabaseOperationOutcome DatabaseOperationOutcomeIncludes = null;

            if (!string.IsNullOrWhiteSpace(this._Compartment) && !string.IsNullOrWhiteSpace(this._CompartmentId))
            {
                PyroSearchParameters CompartmentSearchParameter = ICompartmentSearchParameterService.GetSearchParameters(this._Compartment, this._CompartmentId, IResourceRepository.RepositoryResourceType.GetLiteral());
                DatabaseOperationOutcomeIncludes = IResourceRepository.GetResourceByCompartmentSearch(CompartmentSearchParameter, SearchParameters, true);
            }
            else
            {
                DatabaseOperationOutcomeIncludes = IResourceRepository.GetResourceBySearch(SearchParameters, true);
            }

            //Don't source the same resource again from the Database if we already have it
            if (DatabaseOperationOutcomeIncludes.ReturnedResourceList != null)
            {
                foreach (var Resource in DatabaseOperationOutcomeIncludes.ReturnedResourceList)
                {
                    if (!CacheResourceIDsAlreadyCollected.Contains($"{Resource.ResourceType.Value.GetLiteral()}-{Resource.FhirId}"))
                    {
                        IncludeResourceList.Add(Resource);
                        CacheResourceIDsAlreadyCollected.Add($"{Resource.ResourceType.Value.GetLiteral()}-{Resource.FhirId}");
                    }
                }
            }
        }
示例#2
0
        private void AddIncludeResourceInstanceForIncludes(List <DtoResource> IncludeResourceList, HashSet <string> CacheResourceIDsAlreadyCollected, string FhirId)
        {
            //Don't source the same resource again from the Database if we already have it
            if (!CacheResourceIDsAlreadyCollected.Contains($"{IResourceRepository.RepositoryResourceType.GetLiteral()}-{FhirId}"))
            {
                IDatabaseOperationOutcome DatabaseOperationOutcomeIncludes = null;
                //Here we need to add compartment search, if we have a Compartment and id
                if (!string.IsNullOrWhiteSpace(this._Compartment) && !string.IsNullOrWhiteSpace(this._CompartmentId))
                {
                    //Here we need create a search parameter for _id={FhirId)
                    var IdSearchParameter                      = ServiceSearchParameterFactory.BaseResourceSearchParameters().SingleOrDefault(x => x.Name == "_id");
                    var IdParameterString                      = new Tuple <string, string>(IdSearchParameter.Name, FhirId);
                    ISearchParameterBase SearchParam           = ISearchParameterFactory.CreateSearchParameter(IdSearchParameter, IdParameterString);
                    PyroSearchParameters FhirIdSearchParameter = new PyroSearchParameters();
                    FhirIdSearchParameter.SearchParametersList = new List <ISearchParameterBase>();
                    FhirIdSearchParameter.SearchParametersList.Add(SearchParam);

                    //And now the Compartmnet Search parameters
                    PyroSearchParameters CompartmentSearchParameter = ICompartmentSearchParameterService.GetSearchParameters(this._Compartment, this._CompartmentId, IResourceRepository.RepositoryResourceType.GetLiteral());
                    DatabaseOperationOutcomeIncludes = IResourceRepository.GetResourceByCompartmentSearch(CompartmentSearchParameter, FhirIdSearchParameter, true);
                }
                else
                {
                    DatabaseOperationOutcomeIncludes = IResourceRepository.GetResourceByFhirID(FhirId, true, false);
                }

                var DtoIncludeResourceList = new List <DtoIncludeResource>();
                DatabaseOperationOutcomeIncludes.ReturnedResourceList.ForEach(x => DtoIncludeResourceList.Add(new DtoIncludeResource(x)));
                IncludeResourceList.AddRange(DtoIncludeResourceList);
                CacheResourceIDsAlreadyCollected.Add($"{IResourceRepository.RepositoryResourceType.GetLiteral()}-{FhirId}");
            }
        }
示例#3
0
 public static IQueryable <T> Ordering <T>(this IQueryable <T> query, PyroSearchParameters DtoSearchParameters)
 {
     throw new NotImplementedException();
     //foreach (var SortItem in DtoSearchParameters.SortList)
     //{
     //  //(x => x.lastUpdated)
     //  var type = typeof(T);
     //  string Property = string.Empty;
     //  switch (SortItem.Value.DbSearchParameterType)
     //  {
     //    case Common.Enum.DatabaseEnum.DbIndexType.DateIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.DateTimePeriodIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.NumberIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.QuantityIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.QuantityRangeIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.ReferenceIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.StringIndex:
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.TokenIndex:
     //      Property = SortItem.Value.DbPropertyName + "_Code";
     //      break;
     //    case Common.Enum.DatabaseEnum.DbIndexType.UriIndex:
     //      break;
     //    default:
     //      break;
     //  }
     //}
     //return query;
 }
示例#4
0
        /// <summary>
        ///  Search the loaded resources for the given search parameters
        ///  Note: It is faster to use SearchResourceList as it only indexes for the search parameters provided
        ///  Note: Chain searches do not work in this indexer, only in the databsed indexes
        /// </summary>
        /// <param name="DtoSearchParameters"></param>
        /// <returns></returns>
        public List <IResourceIndexed> SearchLoadedResources(PyroSearchParameters DtoSearchParameters)
        {
            var Predicate          = LinqKit.PredicateBuilder.New <IResourceIndexed>(true);
            var TargetResourceList = MainResourceList.Where(x => x.ResourceType == Common.Tools.ResourceNameResolutionSupport.GetResourceType(DtoSearchParameters.ResourceTarget.GetLiteral()));

            Predicate = ANDSearchParameterListPredicateGenerator(DtoSearchParameters.SearchParametersList);
            IEnumerable <IResourceIndexed> ResultList = TargetResourceList.Where(Predicate);

            return(ResultList.ToList());
        }
示例#5
0
        public Uri GetSelfLink(PyroSearchParameters SearchParameters, string PrimaryServiceRoot, string Container = "", string ContainerId = "")
        {
            string UrlString = PrimaryServiceRoot;

            if (!string.IsNullOrWhiteSpace(Container) && !string.IsNullOrWhiteSpace(ContainerId))
            {
                if (SearchParameters.ResourceTarget.HasValue)
                {
                    UrlString = $"{UrlString}/{Container}/{ContainerId}/{SearchParameters.ResourceTarget.GetLiteral()}";
                }
            }
            else
            {
                if (SearchParameters.ResourceTarget.HasValue)
                {
                    UrlString = $"{UrlString}/{SearchParameters.ResourceTarget.GetLiteral()}";
                }
            }

            bool FirstParameter = true;

            if ((SearchParameters.SearchParametersList != null && SearchParameters.SearchParametersList.Any()) ||
                (SearchParameters.IncludeList != null && SearchParameters.IncludeList.Any() ||
                 SearchParameters.RequiredPageNumber > 0 ||
                 SearchParameters.SummaryType.HasValue) ||
                SearchParameters.CountOfRecordsRequested.HasValue)
            {
                UrlString += "?";
            }

            for (int i = 0; i < SearchParameters.SearchParametersList.Count; i++)
            {
                if (SearchParameters.SearchParametersList[i] is SearchParameterReferance SearchParameterReferance && SearchParameterReferance.IsChained)
                {
                    ////Chained parameters
                    string temp = SearchParameterReferance.RawValue;
                    foreach (var Chain in SearchParameterReferance.ChainedSearchParameterList)
                    {
                        temp += Chain.RawValue;
                    }
                    if (FirstParameter)
                    {
                        UrlString += $"{temp}";
                    }
                    else
                    {
                        UrlString += $"&{UrlString}{temp}";
                    }
                    FirstParameter = false;
                }
示例#6
0
        //Used for Primary Chain Searching
        public string[] GetResourceFhirIdBySearchNoPaging(PyroSearchParameters DtoSearchParameters)
        {
            //var Predicate = LinqKit.PredicateBuilder.New<ResCurrentType>(true);
            //Predicate = PredicateCurrentNotDeleted<ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(Predicate);
            //Predicate = PredicateResourceIdAndLastUpdatedDate<ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList, Predicate);
            //Predicate = ANDSearchParameterListPredicateGenerator<ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList, Predicate);

            var Predicate      = LinqKit.PredicateBuilder.New <ResCurrentType>(true);
            var PredicateOne   = PredicateCurrentNotDeleted <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>();
            var PredicateTwo   = PredicateResourceIdAndLastUpdatedDate <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList);
            var PredicateThree = ANDSearchParameterListPredicateGenerator <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList);

            Predicate = Predicate.And(PredicateOne);
            Predicate = Predicate.And(PredicateTwo);
            Predicate = Predicate.And(PredicateThree);



            var Query = DbGetAll <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(Predicate);

            string[] FhirIdResultArray = Query.Select(x => x.FhirId).ToArray();
            return(FhirIdResultArray);
        }
示例#7
0
        public IDatabaseOperationOutcome GetResourceHistoryByFhirID(string FhirResourceId, PyroSearchParameters DtoSearchParameters)
        {
            IDatabaseOperationOutcome DatabaseOperationOutcome = IDatabaseOperationOutcomeFactory.CreateDatabaseOperationOutcome();

            DatabaseOperationOutcome.SingleResourceRead = false;

            //SetNumberOfRecordsPerPage(DtoSearchParameters);

            var Predicate = LinqKit.PredicateBuilder.New <ResCurrentType>(true);

            Predicate = Predicate.And(x => x.FhirId == FhirResourceId);

            //Query for total count
            int TotalRecordCount = DbGetALLCount <ResCurrentType>(Predicate);

            //Paging set-up
            var Query = DbGetAll <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(Predicate);

            //Which way to order, touchstone tests failing for history due to wrong way, have changed to Descending to see if they pass
            //Query = Query.OrderBy(x => x.LastUpdated);
            Query = Query.OrderByDescending(x => x.LastUpdated);

            int ClaculatedPageRequired = IPagingSupport.CalculatePageRequired(DtoSearchParameters.RequiredPageNumber, DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);

            Query = Query.Paging(ClaculatedPageRequired, IPagingSupport.SetNumberOfRecordsPerPage(DtoSearchParameters.CountOfRecordsRequested));
            int PagesTotal = IPagingSupport.CalculateTotalPages(DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);

            //Query for Resources
            var HistoryEntityList = Query.ToList();

            //Convert to DTO
            var DtoResourceList = new List <DtoResource>();

            if (HistoryEntityList != null)
            {
                HistoryEntityList.ForEach(x => DtoResourceList.Add(IndexSettingSupport.SetDtoResource(x, this.RepositoryResourceType)));
            }

            DatabaseOperationOutcome.SingleResourceRead   = false;
            DatabaseOperationOutcome.SearchTotal          = TotalRecordCount;
            DatabaseOperationOutcome.PagesTotal           = IPagingSupport.CalculateTotalPages(DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);
            DatabaseOperationOutcome.PageRequested        = IPagingSupport.CalculatePageRequired(DtoSearchParameters.RequiredPageNumber, DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);
            DatabaseOperationOutcome.ReturnedResourceList = DtoResourceList;
            return(DatabaseOperationOutcome);
        }
示例#8
0
        public IDatabaseOperationOutcome GetResourceByCompartmentSearch(PyroSearchParameters CompartmentSearchParameters, PyroSearchParameters DtoSearchParameters, bool WithXml = false)
        {
            //SetNumberOfRecordsPerPage(DtoSearchParameters);

            var Predicate = LinqKit.PredicateBuilder.New <ResCurrentType>(true);
            var PredicateCurrentResources = PredicateCurrentNotDeleted <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>();
            var PredicateIdAndLastUpdated = PredicateResourceIdAndLastUpdatedDate <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList);
            var PredicateSearchParameters = ANDSearchParameterListPredicateGenerator <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(DtoSearchParameters.SearchParametersList);
            var PredicateCompartment      = ORSearchParameterListPredicateGenerator <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(CompartmentSearchParameters.SearchParametersList);

            Predicate = Predicate.And(PredicateCurrentResources);
            Predicate = Predicate.And(PredicateIdAndLastUpdated);
            Predicate = Predicate.And(PredicateSearchParameters);
            Predicate = Predicate.And(PredicateCompartment);

            int TotalRecordCount = DbGetALLCount <ResCurrentType>(Predicate);
            var Query            = DbGetAll <ResCurrentType, ResIndexStringType, ResIndexTokenType, ResIndexUriType, ResIndexReferenceType, ResIndexQuantityType, ResIndexDateTimeType>(Predicate);

            //Todo: Sort not implemented just defaulting to last update order
            Query = Query.OrderBy(x => x.LastUpdated);

            int ClaculatedPageRequired = IPagingSupport.CalculatePageRequired(DtoSearchParameters.RequiredPageNumber, DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);

            Query = Query.Paging(ClaculatedPageRequired, IPagingSupport.SetNumberOfRecordsPerPage(DtoSearchParameters.CountOfRecordsRequested));
            var DtoResourceList = new List <DtoResource>();

            if (WithXml)
            {
                DtoResourceList = Query.Select(x => new DtoResource
                {
                    Id           = x.Id,
                    FhirId       = x.FhirId,
                    IsDeleted    = x.IsDeleted,
                    IsCurrent    = true,
                    Version      = x.VersionId,
                    Received     = x.LastUpdated,
                    Method       = x.Method,
                    ResourceType = this.RepositoryResourceType,
                    Xml          = x.XmlBlob
                }).ToList();
            }
            else
            {
                DtoResourceList = Query.Select(x => new DtoResource
                {
                    Id           = x.Id,
                    FhirId       = x.FhirId,
                    IsDeleted    = x.IsDeleted,
                    IsCurrent    = true,
                    Version      = x.VersionId,
                    Received     = x.LastUpdated,
                    Method       = x.Method,
                    ResourceType = this.RepositoryResourceType
                }).ToList();
            }

            IDatabaseOperationOutcome DatabaseOperationOutcome = IDatabaseOperationOutcomeFactory.CreateDatabaseOperationOutcome();

            DatabaseOperationOutcome.SingleResourceRead   = false;
            DatabaseOperationOutcome.SearchTotal          = TotalRecordCount;
            DatabaseOperationOutcome.PagesTotal           = IPagingSupport.CalculateTotalPages(DtoSearchParameters.CountOfRecordsRequested, TotalRecordCount);
            DatabaseOperationOutcome.PageRequested        = ClaculatedPageRequired;
            DatabaseOperationOutcome.ReturnedResourceList = DtoResourceList;
            return(DatabaseOperationOutcome);
        }
示例#9
0
        private List <DtoResource> GetRevIncludes(List <SearchParameterInclude> RevIncludeList, List <DtoResource> CurrentScourceResourceList, HashSet <string> CacheResourceIDsAlreadyCollected)
        {
            var ReturnResourceList = new List <DtoResource>();

            if (RevIncludeList == null || RevIncludeList.Count == 0)
            {
                return(ReturnResourceList);
            }

            if (CurrentScourceResourceList == null || CurrentScourceResourceList.Count == 0)
            {
                return(ReturnResourceList);
            }

            foreach (var Resource in CurrentScourceResourceList)
            {
                //Now process each include
                foreach (var RevInclude in RevIncludeList)
                {
                    PyroSearchParameters SearchParameters = new PyroSearchParameters();
                    SearchParameters.SearchParametersList = new List <ISearchParameterBase>();

                    //Does the include have a target Resource type
                    if (RevInclude.SearchParameterTargetResourceType.HasValue)
                    {
                        //Is the target Resource type of the include == to the current Resource we are targeting
                        if (Resource.ResourceType.Value == RevInclude.SearchParameterTargetResourceType.Value)
                        {
                            IResourceRepository = IRepositorySwitcher.GetRepository(RevInclude.SourceResourceType);
                            foreach (DtoServiceSearchParameterLight p in RevInclude.SearchParameterList)
                            {
                                //Check the current search Parameter has a Target == to the Resource we are targeting
                                if (p.TargetResourceTypeList.Any(x => x.ResourceType.GetLiteral() == Resource.ResourceType.Value.GetLiteral()))
                                {
                                    //Construct the search parameter string
                                    var ParameterString = new Tuple <string, string>(p.Name, $"{RevInclude.SearchParameterTargetResourceType.GetLiteral()}/{Resource.FhirId}");
                                    ISearchParameterBase SearchParam = ISearchParameterFactory.CreateSearchParameter(p, ParameterString);
                                    SearchParameters.SearchParametersList.Clear();
                                    SearchParameters.SearchParametersList.Add(SearchParam);
                                    //Get from the database and only add if we don't already have it
                                    AddIncludeResourceInstanceForRevIncludes(ReturnResourceList, CacheResourceIDsAlreadyCollected, SearchParameters);
                                }
                            }
                        }
                    }
                    else
                    {
                        foreach (DtoServiceSearchParameterLight p in RevInclude.SearchParameterList)
                        {
                            if (p.TargetResourceTypeList.Any(x => x.ResourceType.GetLiteral() == Resource.ResourceType.Value.GetLiteral()))
                            {
                                IResourceRepository = IRepositorySwitcher.GetRepository(ResourceNameResolutionSupport.GetResourceFhirAllType(p.Resource));
                                //Construct the search parameter string
                                var ParameterString = new Tuple <string, string>(p.Name, $"{Resource.ResourceType.Value.GetLiteral()}/{Resource.FhirId}");
                                ISearchParameterBase SearchParam = ISearchParameterFactory.CreateSearchParameter(p, ParameterString);
                                SearchParameters.SearchParametersList.Clear();
                                SearchParameters.SearchParametersList.Add(SearchParam);
                                //Get from the database and only add if we don't already have it
                                AddIncludeResourceInstanceForRevIncludes(ReturnResourceList, CacheResourceIDsAlreadyCollected, SearchParameters);
                            }
                        }
                    }
                }
            }
            return(ReturnResourceList);
        }
示例#10
0
        public void Index(Resource Resource, PyroSearchParameters DtoSearchParameters = null)
        {
            this.ResourceType = Resource.ResourceType;
            this.FhirID       = Resource.Id;
            string ResourceName = Resource.ResourceType.GetLiteral();
            IList <DtoServiceSearchParameterLight> SearchParametersList = IServiceSearchParameterCache.GetSearchParameterForResource(ResourceName);

            //Filter the list by only the searech parameters provided, do not inex for all
            if (DtoSearchParameters != null)
            {
                SearchParametersList = SearchParametersList.Where(x => DtoSearchParameters.SearchParametersList.Any(d => d.Id == x.Id)).ToList();
            }

            PocoNavigator Navigator = new PocoNavigator(Resource);

            string Resource_ResourceName = FHIRAllTypes.Resource.GetLiteral();

            foreach (DtoServiceSearchParameterLight SearchParameter in SearchParametersList)
            {
                //Todo: Composite searchParameters are not supported as yet, need to do work to read
                // the sub search parameters of the composite directly fro the SearchParameter resources.
                if (SearchParameter.Type != SearchParamType.Composite)
                {
                    bool SetSearchParameterIndex = true;
                    //if ((SearchParameter.Resource == Resource_ResourceName && SearchParameter.Name == "_id") ||
                    //  (SearchParameter.Resource == Resource_ResourceName && SearchParameter.Name == "_lastUpdated"))
                    //{
                    //  SetSearchParameterIndex = false;
                    //}

                    if (SetSearchParameterIndex)
                    {
                        string Expression = SearchParameter.Expression;
                        if (SearchParameter.Resource == Resource_ResourceName)
                        {
                            //If the Expression is one with a parent resource of Resource then swap it for the actual current resource name
                            //For example make 'Resource._tag' be 'Observation._tag' for Observation resources.
                            Expression = Resource.TypeName + SearchParameter.Expression.TrimStart(Resource_ResourceName.ToCharArray());
                        }

                        IEnumerable <IElementNavigator> ResultList = Navigator.Select(Expression, new EvaluationContext(Navigator));
                        foreach (IElementNavigator oElement in ResultList)
                        {
                            if (oElement != null)
                            {
                                switch (SearchParameter.Type)
                                {
                                case SearchParamType.Number:
                                {
                                    this.IndexQuantityList.AddRange(IIndexSetterFactory.CreateNumberSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.Date:
                                {
                                    this.IndexDateTimeList.AddRange(IIndexSetterFactory.CreateDateTimeSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.String:
                                {
                                    this.IndexStringList.AddRange(IIndexSetterFactory.CreateStringSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.Token:
                                {
                                    this.IndexTokenList.AddRange(IIndexSetterFactory.CreateTokenSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.Reference:
                                {
                                    this.IndexReferenceList.AddRange(IIndexSetterFactory.CreateReferenceSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.Composite:
                                {
                                    break;
                                }

                                case SearchParamType.Quantity:
                                {
                                    this.IndexQuantityList.AddRange(IIndexSetterFactory.CreateQuantitySetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                case SearchParamType.Uri:
                                {
                                    this.IndexUriList.AddRange(IIndexSetterFactory.CreateUriSetter().Set(oElement, SearchParameter));
                                    break;
                                }

                                default:
                                    throw new System.ComponentModel.InvalidEnumArgumentException(SearchParameter.Type.ToString(), (int)SearchParameter.Type, typeof(SearchParamType));
                                }
                            }
                        }
                    }
                }
            }
        }
示例#11
0
        public ISmartScopeOutcome ProcessScopes(PyroSearchParameters PyroSearchParameters, FHIRAllTypes ServiceResourceType, bool Read, bool Write)
        {
            ISmartScopeOutcome SmartScopeOutcome = new SmartScopeOutcome()
            {
                ScopesOK = false
            };

            // If FHIRApiAuthentication = false then no need to check and scopes, ScopesOK!
            if (!IGlobalProperties.FHIRApiAuthentication)
            {
                SmartScopeOutcome.ScopesOK = true;
                return(SmartScopeOutcome);
            }

            SmartEnum.Action SmartAction = GetActionEnum(Read, Write);

            if (System.Threading.Thread.CurrentPrincipal != null && System.Threading.Thread.CurrentPrincipal is ClaimsPrincipal Principal)
            {
                //Get Client Id, we need to log this somewere, maybe FHIR AuditEventy?
                System.Security.Claims.Claim ClientClaim = Principal.Claims.SingleOrDefault(x => x.Type == ClientIdName);

                //Get tye scopes
                List <System.Security.Claims.Claim> ScopeClaim = Principal.Claims.Where(x => x.Type == ScopeName).ToList();

                //This should be injected
                ScopeParse         ScopeParse = new ScopeParse();
                List <ISmartScope> ScopeList  = new List <ISmartScope>();
                foreach (var ScopeString in ScopeClaim)
                {
                    ISmartScope SmartScope = new SmartScope();
                    if (ScopeParse.Parse(ScopeString.Value, out SmartScope))
                    {
                        ScopeList.Add(SmartScope);
                    }
                    else
                    {
                        string Message = $"Unable to parse the SMART on FHIR scope given. Scope was {ScopeString.Value}";
                        var    OpOut   = Common.Tools.FhirOperationOutcomeSupport.Create(OperationOutcome.IssueSeverity.Error, OperationOutcome.IssueType.Exception, Message);
                        throw new Common.Exceptions.PyroException(System.Net.HttpStatusCode.InternalServerError, OpOut, Message);
                    }
                }

                IEnumerable <ISmartScope> FoundScopesList = ScopeList.Where(x => x.Resource == ServiceResourceType && (x.Action == SmartAction || x.Action == SmartEnum.Action.All));
                if (FoundScopesList.Count() > 0)
                {
                    if (PyroSearchParameters.IncludeList != null && PyroSearchParameters.IncludeList.Count > 0)
                    {
                        foreach (var Include in PyroSearchParameters.IncludeList)
                        {
                            FoundScopesList = ScopeList.Where(x => x.Resource == Include.SourceResourceType && (x.Action == SmartAction || x.Action == SmartEnum.Action.All));
                            if (FoundScopesList.Count() == 0)
                            {
                                //Reject
                                string Message = $"You do not have permission to access the {Include.SourceResourceType.GetLiteral()} Resource type found within your include or revinclude search parameters.";
                                var    OpOut   = Common.Tools.FhirOperationOutcomeSupport.Create(OperationOutcome.IssueSeverity.Error, OperationOutcome.IssueType.Forbidden, Message);
                                SmartScopeOutcome.OperationOutcome = OpOut;
                                SmartScopeOutcome.ScopesOK         = false;
                                return(SmartScopeOutcome);
                            }
                        }
                    }

                    var SearchParametersThatHaveChainParametersList = PyroSearchParameters.SearchParametersList.Where(x => x.ChainedSearchParameter != null);
                    if (SearchParametersThatHaveChainParametersList != null && SearchParametersThatHaveChainParametersList.Count() > 0)
                    {
                        foreach (ISearchParameterBase Chain in SearchParametersThatHaveChainParametersList)
                        {
                            string ResourceWithNoScopeAccess = RecursiveChainScoped(Chain, ScopeList, SmartAction);
                            if (!string.IsNullOrWhiteSpace(ResourceWithNoScopeAccess))
                            {
                                //Reject
                                string Message = $"You do not have permission to access {ResourceWithNoScopeAccess} resources types which was one of the resources types within your chained search parameter.";
                                var    OpOut   = Common.Tools.FhirOperationOutcomeSupport.Create(OperationOutcome.IssueSeverity.Error, OperationOutcome.IssueType.Forbidden, Message);
                                SmartScopeOutcome.OperationOutcome = OpOut;
                                SmartScopeOutcome.ScopesOK         = false;
                                return(SmartScopeOutcome);
                            }
                        }
                    }

                    //ALL GOOD! We have a scope for the resource and action. all ok.
                    SmartScopeOutcome.ScopesOK = true;
                    return(SmartScopeOutcome);
                }
                else
                {
                    string Message = string.Empty;
                    if (SmartAction == SmartEnum.Action.All)
                    {
                        Message = $"You do not have permission to access Resources {ServiceResourceType.GetLiteral()} types for Read or Write.";
                    }
                    else if (SmartAction == SmartEnum.Action.Read)
                    {
                        Message = $"You do not have permission to access Resources {ServiceResourceType.GetLiteral()} types for Read.";
                    }
                    else if (SmartAction == SmartEnum.Action.Read)
                    {
                        Message = $"You do not have permission to access Resources {ServiceResourceType.GetLiteral()} types for Write.";
                    }
                    var OpOut = Common.Tools.FhirOperationOutcomeSupport.Create(OperationOutcome.IssueSeverity.Error, OperationOutcome.IssueType.Forbidden, Message);
                    SmartScopeOutcome.OperationOutcome = OpOut;
                    SmartScopeOutcome.ScopesOK         = false;
                    return(SmartScopeOutcome);
                }
            }
            else
            {
                //System.Threading.Thread.CurrentPrincipal was null
                string Message = "Internal Server Error: System.Threading.Thread.CurrentPrincipal was null";
                var    OpOut   = Common.Tools.FhirOperationOutcomeSupport.Create(OperationOutcome.IssueSeverity.Error, OperationOutcome.IssueType.Exception, Message);
                throw new Common.Exceptions.PyroException(System.Net.HttpStatusCode.InternalServerError, OpOut, Message);
            }
        }
示例#12
0
        public bool ResolveChain(ISearchParameterReferance SearchParameterReferance)
        {
            bool ChainTargetFound = true;

            if (!SearchParameterReferance.IsChained)
            {
                throw new Exception("Server Error: SearchParameterReferance.IsChained must be true for ChainSearchingService.");
            }

            IEnumerable <string> FhirIdList = null;
            //Work through each chain parameter in reverse
            bool PrimarySearchPerfomed = false;

            for (int i = SearchParameterReferance.ChainedSearchParameterList.Count - 1; i >= 0; i--)
            {
                ISearchParameterBase SearchParameterBase = SearchParameterReferance.ChainedSearchParameterList[i];
                //When the Chained parameter is a parameter for all resource types we need to switch the TypeModifierResource given for the
                //previous chain parameter or the root parameter
                //for example 'Observation?subject:Patient._id=FCC-PAT-0001'
                //Here the _id is an all Resource type search parameter so it's SearchParameterBase.Resource = Resource, we need here to refer to the
                //given SearchParameterReferance.TypeModifierResource as seen in the search string ':Patient'
                //Another example is 'DiagnosticReport?result:Observation.subject:Patient._id=FCC-PAT-00001' where the need to get the previous TypeModifierResource
                //from the list of chain parameters or the root parameter when i = 0.
                //so for this last example we need ':Patient' for the '_id' and ':Observation' for the 'subject'
                string ResourceRequiredForRepository = string.Empty;
                if (i > 0)
                {
                    ResourceRequiredForRepository = ResolveResourceTypeFromSearchParameterResourceModifier(SearchParameterBase.Resource, SearchParameterReferance.ChainedSearchParameterList[i - 1].TypeModifierResource);
                }
                else
                {
                    ResourceRequiredForRepository = ResolveResourceTypeFromSearchParameterResourceModifier(SearchParameterBase.Resource, SearchParameterReferance.TypeModifierResource);
                }

                if (!PrimarySearchPerfomed)
                {
                    IResourceRepository = IRepositorySwitcher.GetRepository(ResourceNameResolutionSupport.GetResourceFhirAllType(ResourceRequiredForRepository));
                    PyroSearchParameters SearchParameters = new PyroSearchParameters();
                    SearchParameters.SearchParametersList = new List <ISearchParameterBase>()
                    {
                        SearchParameterBase
                    };
                    FhirIdList            = IResourceRepository.GetResourceFhirIdBySearchNoPaging(SearchParameters);
                    PrimarySearchPerfomed = true;
                    if (FhirIdList.Count() == 0)
                    {
                        ChainTargetFound = false;
                        break;
                    }
                }
                else
                {
                    IResourceRepository = IRepositorySwitcher.GetRepository(ResourceNameResolutionSupport.GetResourceFhirAllType(ResourceRequiredForRepository));
                    string ReferenceResourceTargetName = string.Empty;
                    if (string.IsNullOrWhiteSpace(SearchParameterBase.TypeModifierResource))
                    {
                        ReferenceResourceTargetName = SearchParameterBase.TargetResourceTypeList[0].ResourceType.GetLiteral();
                    }
                    else
                    {
                        ReferenceResourceTargetName = SearchParameterBase.TypeModifierResource;
                    }
                    FhirIdList = IResourceRepository.GetResourceFhirIdByReferanceIndex(FhirIdList, ReferenceResourceTargetName, SearchParameterBase.Id);
                    if (FhirIdList.Count() == 0)
                    {
                        ChainTargetFound = false;
                        break;
                    }
                }
            }

            if (ChainTargetFound)
            {
                //We use the resource type from the first in the list which was the last above because we Reversed the list in the for each loop above.
                string ResourceType = ResolveResourceTypeFromSearchParameterResourceModifier(SearchParameterReferance.ChainedSearchParameterList[0].Resource, SearchParameterReferance.TypeModifierResource);
                SetSearchParameterValueList(FhirIdList, ResourceType, SearchParameterReferance);
            }
            return(ChainTargetFound);
        }
示例#13
0
 public List <IResourceIndexed> SearchKeyedResourceList(Dictionary <string, Resource> ResourceDictonary, PyroSearchParameters DtoSearchParameters)
 {
     MainResourceList = new List <IResourceIndexed>();
     foreach (var DicItem in ResourceDictonary)
     {
         if (DicItem.Value.ResourceType == Common.Tools.ResourceNameResolutionSupport.GetResourceType(DtoSearchParameters.ResourceTarget.GetLiteral()))
         {
             var ResourceIndexed = IGenericInstanceFactory.Create <IResourceIndexed>();
             ResourceIndexed.Index(DicItem.Value, DtoSearchParameters);
             ResourceIndexed.Key = DicItem.Key;
             MainResourceList.Add(ResourceIndexed);
         }
     }
     return(SearchLoadedResources(DtoSearchParameters));
 }
示例#14
0
 /// <summary>
 /// This method only indexes for the search parameters provided, so it is faster that  LoadResource followed by Search.
 /// Note: Chain searches do not work in this indexer, only in the databsed indexes
 /// </summary>
 /// <param name="ResourceList"></param>
 /// <param name="DtoSearchParameters"></param>
 /// <returns></returns>
 public List <IResourceIndexed> SearchResourceList(ICollection <Resource> ResourceList, PyroSearchParameters DtoSearchParameters)
 {
     MainResourceList = new List <IResourceIndexed>();
     foreach (Resource Res in ResourceList)
     {
         if (Res.ResourceType == Common.Tools.ResourceNameResolutionSupport.GetResourceType(DtoSearchParameters.ResourceTarget.GetLiteral()))
         {
             var ResourceIndexed = IGenericInstanceFactory.Create <IResourceIndexed>();
             ResourceIndexed.Index(Res, DtoSearchParameters);
             MainResourceList.Add(ResourceIndexed);
         }
     }
     return(SearchLoadedResources(DtoSearchParameters));
 }