示例#1
0
        //param childIndexName may have an integer on the end if >1 sibling with same name (e.g. NTE2)
        private void ParseReps(XmlElement groupElement, IGroup groupObject, String messageName, String childName,
                               String childIndexName)
        {
            IList reps = GetChildElementsByTagName(groupElement, MakeGroupElementName(messageName, childName));

            log.Debug("# of elements matching " + MakeGroupElementName(messageName, childName) + ": " + reps.Count);

            if (groupObject.IsRepeating(childIndexName))
            {
                for (int i = 0; i < reps.Count; i++)
                {
                    ParseRep((XmlElement)reps[i], groupObject.GetStructure(childIndexName, i));
                }
            }
            else
            {
                if (reps.Count > 0)
                {
                    ParseRep((XmlElement)reps[0], groupObject.GetStructure(childIndexName, 0));
                }

                if (reps.Count > 1)
                {
                    String newIndexName = groupObject.addNonstandardSegment(childName);
                    for (int i = 1; i < reps.Count; i++)
                    {
                        ParseRep((XmlElement)reps[i], groupObject.GetStructure(newIndexName, i - 1));
                    }
                }
            }
        }
示例#2
0
        /// <summary>
        /// param childIndexName may have an integer on the end if >1 sibling with same name (e.g. NTE2)
        /// </summary>
        ///
        /// <param name="theElem">  Element describing the. </param>
        /// <param name="theObj">   the object. </param>

        private void ParseRep(System.Xml.XmlElement theElem, IStructure theObj)
        {
            if (theObj is IGroup)
            {
                this.Parse((IGroup)theObj, theElem);
            }
            else if (theObj is ISegment)
            {
                this.Parse((ISegment)theObj, theElem);
            }
            log.Debug("Parsed element: " + theElem.Name);
        }
示例#3
0
        /// <summary> Finds a message or segment class by name and version.</summary>
        /// <param name="name">the segment or message structure name.
        /// </param>
        /// <param name="version">the HL7 version.
        /// </param>
        /// <param name="type">'message', 'group', 'segment', or 'datatype'.
        /// </param>
        private static Type FindClass(string name, string version, ClassType type)
        {
            if (ParserBase.ValidVersion(version) == false)
            {
                throw new HL7Exception("The HL7 version " + version + " is not recognized", ErrorCode.UNSUPPORTED_VERSION_ID);
            }

            // get list of packages to search for the corresponding message class
            var packages = PackageList(version);

            // get sub-package for component type
            var typeString = type.ToString();
            var subpackage = typeString.Substring(0, 1).ToUpper() + typeString.Substring(1);

            // try to load class from each package
            Type compClass = null;
            var  c         = 0;

            while (compClass == null && c < packages.Count)
            {
                try
                {
                    var p = packages[c];
                    if (!p.EndsWith("."))
                    {
                        p = p + ".";
                    }

                    var classNameToTry = p + subpackage + "." + name;

                    classNameToTry = AddAssemblyName(p, classNameToTry);
                    if (Log.DebugEnabled)
                    {
                        Log.Debug("Trying to load: " + classNameToTry);
                    }

                    compClass = Type.GetType(classNameToTry);
                    if (Log.DebugEnabled)
                    {
                        Log.Debug("Loaded: " + classNameToTry + " class: " + compClass);
                    }
                }
                catch (Exception)
                {
                    /* just try next one */
                }

                c++;
            }

            return(compClass);
        }
示例#4
0
        /// <summary> Populates the given error segment with information from this Exception.</summary>
        public virtual void populate(ISegment errorSegment)
        {
            //make sure it's an ERR
            if (!errorSegment.GetStructureName().Equals("ERR"))
            {
                throw new HL7Exception("Can only populate an ERR segment with an exception -- got: " +
                                       errorSegment.GetType().FullName);
            }

            int rep = errorSegment.GetField(1).Length;             //append after existing reps

            if (SegmentName != null)
            {
                Terser.Set(errorSegment, 1, rep, 1, 1, SegmentName);
            }

            if (SegmentRepetition >= 0)
            {
                Terser.Set(errorSegment, 1, rep, 2, 1, Convert.ToString(SegmentRepetition));
            }

            if (FieldPosition >= 0)
            {
                Terser.Set(errorSegment, 1, rep, 3, 1, Convert.ToString(FieldPosition));
            }

            Terser.Set(errorSegment, 1, rep, 4, 1, Convert.ToString(errCode));
            Terser.Set(errorSegment, 1, rep, 4, 3, "hl70357");
            Terser.Set(errorSegment, 1, rep, 4, 5, Message);

            //try to get error condition text
            try
            {
                String desc = TableRepository.Instance.getDescription(357, Convert.ToString(errCode));
                Terser.Set(errorSegment, 1, rep, 4, 2, desc);
            }
            catch (LookupException e)
            {
                ourLog.Debug("Warning: LookupException getting error condition text (are we connected to a TableRepository?)", e);
            }
            catch (InvalidOperationException e)
            {
                ourLog.Debug("Warning: InvalidOperationException getting error condition text (are we connected to a TableRepository? Is a valid ConnectionString configured?)", e);
            }
        }
示例#5
0
 private static void SetObx2Fallback(IPrimitive obx2, ISegment segment, ParserOptions parserOptions)
 {
     if (obx2.Value == null)
     {
         if (!(parserOptions.DefaultObx2Type is null))
         {
             Log.Debug($"setting default {segment.GetStructureName()}-{2} type to {parserOptions.DefaultObx2Type}");
             obx2.Value = parserOptions.DefaultObx2Type;
         }
     }
 }
示例#6
0
        /// <summary> Sets the string value of the field specified.  See class docs for location spec syntax.</summary>
        public virtual void Set(System.String spec, System.String value_Renamed)
        {
            SupportClass.Tokenizer tok = new SupportClass.Tokenizer(spec, "-", false);
            ISegment segment           = getSegment(tok.NextToken());

            int[] ind = getIndices(spec);
            if (log.DebugEnabled)
            {
                log.Debug("Setting " + spec + " seg: " + segment.GetStructureName() + " ind: " + ind[0] + " " + ind[1] + " " + ind[2] + " " + ind[3]);
            }
            Set(segment, ind[0], ind[1], ind[2], ind[3], value_Renamed);
        }
示例#7
0
        /// <summary> Parses a message string and returns the corresponding Message
        /// object.  Unexpected segments added at the end of their group.
        ///
        /// </summary>
        /// <throws>  HL7Exception if the message is not correctly formatted. </throws>
        /// <throws>  EncodingNotSupportedException if the message encoded </throws>
        /// <summary>      is not supported by this parser.
        /// </summary>
        protected internal override IMessage DoParse(System.String message, System.String version)
        {
            //try to instantiate a message object of the right class
            MessageStructure structure = GetStructure(message);
            IMessage         m         = InstantiateMessage(structure.messageStructure, version, structure.explicitlyDefined);

            //MessagePointer ptr = new MessagePointer(this, m, getEncodingChars(message));
            MessageIterator messageIter = new MessageIterator(m, "MSH", true);

            FilterIterator.IPredicate segmentsOnly = new AnonymousClassPredicate(this);
            FilterIterator            segmentIter  = new FilterIterator(messageIter, segmentsOnly);

            System.String[]    segments      = Split(message, segDelim);
            EncodingCharacters encodingChars = GetEncodingChars(message);

            for (int i = 0; i < segments.Length; i++)
            {
                //get rid of any leading whitespace characters ...
                if (segments[i] != null && segments[i].Length > 0 && System.Char.IsWhiteSpace(segments[i][0]))
                {
                    segments[i] = StripLeadingWhitespace(segments[i]);
                }

                //sometimes people put extra segment delimiters at end of msg ...
                if (segments[i] != null && segments[i].Length >= 3)
                {
                    System.String name = segments[i].Substring(0, (3) - (0));
                    log.Debug("Parsing segment " + name);

                    messageIter.Direction = name;
                    FilterIterator.IPredicate byDirection = new AnonymousClassPredicate1(name, this);
                    FilterIterator            dirIter     = new FilterIterator(segmentIter, byDirection);
                    if (dirIter.MoveNext())
                    {
                        Parse((ISegment)dirIter.Current, segments[i], encodingChars);
                    }
                }
            }
            return(m);
        }
示例#8
0
        /* for configurability (maybe to add later, replacing hard-coded options
         * in nextFromEndOfGroup) ...
         * public void setSearchLevel(String level) {
         * if (WHOLE_GROUP.equals(level)) {
         * this.findUpToFirstRequired = false;
         * this.findFirstDescendentsOnly = false;
         * } else if (FIRST_DESCENDENTS_ONLY.equals(level)) {
         * this.findUpToFirstRequired = false;
         * this.findFirstDescendentsOnly = true;
         * } else if (UP_TO_FIRST_REQUIRED.equals(level)) {
         * this.findUpToFirstRequired = true;
         * this.findFirstDescendentsOnly = false;
         * } else {
         * throw IllegalArgumentException(level + " is not a valid search level.  Should be WHOLE_GROUP, etc.");
         * }
         * }
         *
         * public String getSearchLevel() {
         * String level = WHOLE_GROUP;
         * if (this.findFirstDescendentsOnly) {
         * level = FIRST_DESCENDENTS_ONLY;
         * } else if (this.findUpTpFirstRequired) {
         * level = UP_TO_FIRST_REQUIRED;
         * }
         * return level;
         * }*/


        /// <summary> Returns true if another object exists in the iteration sequence.  </summary>
        public virtual bool MoveNext()
        {
            bool has = true;

            if (next_Renamed_Field == null)
            {
                if (typeof(IGroup).IsAssignableFrom(currentStructure.GetType()))
                {
                    groupNext((IGroup)currentStructure);
                }
                else
                {
                    IGroup   parent          = currentStructure.ParentStructure;
                    Index    i               = getIndex(parent, currentStructure);
                    Position currentPosition = new Position(parent, i);

                    try
                    {
                        if (parent.IsRepeating(i.name) && currentStructure.GetStructureName().Equals(direction))
                        {
                            nextRep(currentPosition);
                        }
                        else
                        {
                            has = nextPosition(currentPosition, this.direction, this.handleUnexpectedSegments);
                        }
                    }
                    catch (HL7Exception e)
                    {
                        throw new System.ApplicationException("HL7Exception arising from bad index: " + e.Message);
                    }
                }
            }
            log.Debug("MessageIterator.hasNext() in direction " + this.direction + "? " + has);
            return(has);
        }
示例#9
0
        /// <summary> Populates the given Segment object with data from the given XML Element.</summary>
        /// <throws>  HL7Exception if the XML Element does not have the correct name and structure </throws>
        /// <summary>      for the given Segment, or if there is an error while setting individual field values.
        /// </summary>
        public virtual void Parse(ISegment segmentObject, XmlElement segmentElement)
        {
            SupportClass.HashSetSupport done = new SupportClass.HashSetSupport();

            //        for (int i = 1; i <= segmentObject.NumFields(); i++) {
            //            String elementName = makeElementName(segmentObject, i);
            //            done.add(elementName);
            //            parseReps(segmentObject, segmentElement, elementName, i);
            //        }

            XmlNodeList all = segmentElement.ChildNodes;

            for (int i = 0; i < all.Count; i++)
            {
                String elementName = all.Item(i).Name;
                if (Convert.ToInt16(all.Item(i).NodeType) == (short)XmlNodeType.Element && !done.Contains(elementName))
                {
                    done.Add(elementName);

                    int index = elementName.IndexOf('.');
                    if (index >= 0 && elementName.Length > index)
                    {
                        //properly formatted element
                        String fieldNumString = elementName.Substring(index + 1);
                        int    fieldNum       = Int32.Parse(fieldNumString);
                        ParseReps(segmentObject, segmentElement, elementName, fieldNum);
                    }
                    else
                    {
                        log.Debug("Child of segment " + segmentObject.GetStructureName() + " doesn't look like a field: " + elementName);
                    }
                }
            }

            //set data type of OBX-5
            if (segmentObject.GetType().FullName.IndexOf("OBX") >= 0)
            {
                Varies.fixOBX5(segmentObject, Factory);
            }
        }