Beispiel #1
0
        public void CloneTest()
        {
            Record target = new Record();
            Record expected = target;
            Record actual;
            actual = target.Clone();
            Assert.AreNotEqual(expected, actual);

            target.Leader = "Take me to your leader!";

            string expectedString = string.Empty.PadRight(FileMARC.LEADER_LEN);
            string actualString;
            actualString = actual.Leader;
            Assert.AreEqual(expectedString, actualString);

            target.Warnings.Add("Testing!");

            int expectedCount = 0;
            int actualCount;
            actualCount = actual.Warnings.Count;
            Assert.AreEqual(expectedCount, actualCount);

            target.Fields.Add(new ControlField("001", "Test Data"));

            expectedCount = 0;
            actualCount = actual.Fields.Count;
            Assert.AreEqual(expectedCount, actualCount);
        }
Beispiel #2
0
        /// <summary>
        /// Decodes the raw MARC record into a <see cref="MARC.Record"/> at the specified index.///
        /// </summary>
        /// <param name="index">The index of the record to retrieve.</param>
        /// <returns></returns>
        private Record Decode(int index)
        {
            XElement record = _rawSource[index];
            Record marcXml = new Record();

            //First we get the leader
            marcXml.Leader = record.Elements().First(e => e.Name.LocalName == "leader").Value;

            //Now we get the control fields
            foreach (XElement controlField in record.Elements().Where(e => e.Name.LocalName == "controlfield"))
            {
                ControlField newField = new ControlField(controlField.Attribute("tag").Value, controlField.Value);
                marcXml.Fields.Add(newField);
            }

            //Now we get the data fields
            foreach (XElement dataField in record.Elements().Where(e => e.Name.LocalName == "datafield"))
            {
                DataField newField = new DataField(dataField.Attribute("tag").Value, new List<Subfield>(), dataField.Attribute("ind1").Value[0], dataField.Attribute("ind2").Value[0]);

                foreach (XElement subfield in dataField.Elements().Where(e => e.Name.LocalName == "subfield"))
                {
                    Subfield newSubfield = new Subfield(subfield.Attribute("code").Value[0], subfield.Value);
                    newField.Subfields.Add(newSubfield);
                }

                marcXml.Fields.Add(newField);
            }

            return marcXml;
        }
Beispiel #3
0
 public void WarningsTest()
 {
     Record target = new Record();
     string expected = "IT'S ALL BROKEN! SOUND THE ALARM!";
     target.AddWarnings("IT'S ALL BROKEN! SOUND THE ALARM!");
     List<string> actual;
     actual = target.Warnings;
     Assert.AreEqual(expected, actual[0]);
 }
Beispiel #4
0
 public void ToRawTest()
 {
     Record target = new Record();
     target.Fields.Add(new ControlField("001", "I am data! (But not Data from Star Trek TNG)"));
     //This will be empty, and thus not written
     target.Fields.Add(new DataField("245"));
     //I broke each bit of the record out into their own strings and concatenated because it's easier to follow.
     //Leader -> Tag -> Length (+1 for EoF) -> Starts At -> EoF -> Data -> EoF -> EoR
     string expected = "00083     2200037   4500" + "001" + "0045" + "00000" + FileMARC.END_OF_FIELD + "I am data! (But not Data from Star Trek TNG)" + FileMARC.END_OF_FIELD + FileMARC.END_OF_RECORD;
     string actual;
     actual = target.ToRaw();
     Assert.AreEqual(expected, actual);
 }
Beispiel #5
0
 public void ToStringTest()
 {
     Record target = new Record();
     target.Fields.Add(new ControlField("001", "I am data! (But not Data from Star Trek TNG)"));
     //This will be empty, and thus not written
     target.Fields.Add(new DataField("245"));
     string expected = "LDR 00083     2200037   4500" + Environment.NewLine +
                       "001" + "     " + "I am data! (But not Data from Star Trek TNG)" + Environment.NewLine;
     string actual;
     actual = target.ToString();
     Assert.AreEqual(expected, actual);
 }
Beispiel #6
0
 public void LeaderTest()
 {
     Record target = new Record();
     string expected = "Take me to your leader!";
     string actual;
     target.Leader = expected;
     actual = target.Leader;
     Assert.AreEqual(expected, actual);
 }
Beispiel #7
0
        public void RecordConstructorTest()
        {
            Record target = new Record();

            {
                int expected = 0;
                int actual = target.Fields.Count;
                Assert.AreEqual(expected, actual);
                actual = target.Warnings.Count;
                Assert.AreEqual(expected, actual);
            }

            {
                string expected = "                        "; //24 spaces! Yes I counted! :awesome:
                string actual = target.Leader;
                Assert.AreEqual(expected, actual);
            }
        }
Beispiel #8
0
 public void InsertFieldTest()
 {
     Record target = new Record();
     string tag = "245";
     target.Fields.Add(new ControlField("001", "I am data! (But not Data from Star Trek TNG)"));
     target.Fields.Add(new DataField(tag));
     target.Fields.Add(new DataField("521", new List<Subfield>(), ' ', '1'));
     Field newField = new DataField("300", new List<Subfield>(), '0', '1');
     target.InsertField(newField);
     Assert.AreSame(newField, target.Fields[2]);
 }
Beispiel #9
0
 public void ItemTest()
 {
     Record target = new Record();
     string tag = "245";
     ControlField controlField = new ControlField("001", "I am data! (But not Data from Star Trek TNG)");
     DataField dataField = new DataField(tag);
     DataField dataField2 = new DataField(tag, new List<Subfield>(), ' ', '1');
     target.Fields.Add(controlField);
     target.Fields.Add(dataField);
     target.Fields.Add(dataField2);
     Field expected = dataField;
     Field actual;
     actual = target[tag];
 }
Beispiel #10
0
 public void GetFieldsTest()
 {
     Record target = new Record();
     string tag = "245";
     target.Fields.Add(new ControlField("001", "I am data! (But not Data from Star Trek TNG)"));
     target.Fields.Add(new DataField(tag));
     target.Fields.Add(new DataField("521", new List<Subfield>(), ' ', '1'));
     List<Field> expected = new List<Field>();
     expected.Add(new DataField(tag));
     List<Field> actual;
     actual = target.GetFields(tag);
     Assert.AreEqual(expected.Count, actual.Count);
     Assert.AreEqual(expected[0].ToRaw(), actual[0].ToRaw());
 }
Beispiel #11
0
        public void FieldsTest()
        {
            Record target = new Record();
            ControlField controlField = new ControlField("001", "I am data! (But not Data from Star Trek TNG)");
            DataField dataField = new DataField("245");
            DataField dataField2 = new DataField("521", new List<Subfield>(), ' ', '1');
            target.Fields.Add(controlField);
            target.Fields.Add(dataField);
            target.Fields.Add(dataField2);

            {
                int expected = 3;
                int actual;
                actual = target.Fields.Count;
                Assert.AreEqual(expected, actual);
            }

            {
                Field expected = controlField;
                Field actual;
                actual = target.Fields[0];
                Assert.AreSame(expected, actual);
                expected = dataField;
                actual = target.Fields[1];
                Assert.AreSame(expected, actual);
                expected = dataField2;
                actual = target.Fields[2];
                Assert.AreSame(expected, actual);
            }

            {
                List<Field> expected = new List<Field>();
                expected.Add(controlField);
                expected.Add(dataField);
                expected.Add(dataField2);
                target.Fields = expected;
                List<Field> actual;
                actual = target.Fields;
                Assert.AreSame(expected, actual);
            }
        }
Beispiel #12
0
        /// <summary>
        /// Decodes the raw MARC record into a <see cref="MARC.Record"/> at the specified index.///
        /// </summary>
        /// <param name="index">The index of the record to retrieve.</param>
        /// <returns></returns>
        private Record Decode(int index)
        {
            string raw = _rawSource[index];
            Record marc = new Record();
            Match match = Regex.Match(raw, "^(\\d{5})");
            int recordLength = 0;

            // Store record length
            if (match.Captures.Count == 0)
                marc.AddWarnings("MARC record length is not numeric.");
            else
                recordLength = Convert.ToInt32(match.Captures[0].Value);

            if (recordLength != raw.Length)
            {
                marc.AddWarnings("MARC record length does not match actual length.");
                recordLength = raw.Length;
            }

            if (!raw.EndsWith(END_OF_RECORD.ToString()))
                throw new InvalidDataException("MARC record ends with an invalid terminator");

            //Store leader
            marc.Leader = raw.Substring(0, LEADER_LEN);

            //Bytes 12-16 of leader give offset to the body of the record
            int dataStart = Convert.ToInt32(raw.Substring(12, 5));

            //Immediately after the leader comes the directory (no separator)
            string directory = raw.Substring(LEADER_LEN, dataStart - LEADER_LEN - 1);

            //Character after the directory should be END_OF_FIELD
            if (raw.Substring(dataStart - 1, 1) != END_OF_FIELD.ToString())
                marc.AddWarnings("No directory found.");

            //All directory entries must be DIRECTORY_ENTRY_LEN long, so length % DIRECTORY_ENTRY_LEN should be 0
            if (directory.Length % DIRECTORY_ENTRY_LEN != 0)
                marc.AddWarnings("Invalid directory length.");

            //Go through all the fields
            int fieldCount = directory.Length / DIRECTORY_ENTRY_LEN;

            for (int i = 0; i < fieldCount; i++)
            {
                string tag = directory.Substring(i * DIRECTORY_ENTRY_LEN, DIRECTORY_ENTRY_LEN).Substring(0, 3);
                int fieldLength = 0;
                int fieldOffset = 0;
                try
                {
                    fieldLength = Convert.ToInt32(directory.Substring(i * DIRECTORY_ENTRY_LEN, DIRECTORY_ENTRY_LEN).Substring(3, 4));
                }
                catch (FormatException)
                {
                    marc.AddWarnings("Invalid Directory Tag Length for tag " + tag + ".");
                }

                try
                {
                    fieldOffset = Convert.ToInt32(directory.Substring(i * DIRECTORY_ENTRY_LEN, DIRECTORY_ENTRY_LEN).Substring(7, 5));
                }
                catch (FormatException)
                {
                    marc.AddWarnings("Invalid Directory Offset for tag " + tag + ".");
                }

                //Check Directory validity

                //If a tag isn't valid, default it to ZZZ. This should at least make the record valid enough to be readable and not throw exceptions
                if (!Field.ValidateTag(tag))
                {
                    marc.AddWarnings("Invalid tag " + tag + " in directory.");
                    tag = "ZZZ";
                }

                if (fieldOffset + fieldLength > recordLength)
                    marc.AddWarnings("Directory entry for tag " + tag + " runs past the end of the record.");

                int fieldStart = dataStart + fieldOffset;
                if (fieldStart > recordLength)
                {
                    marc.AddWarnings("Directory entry for tag " + tag + " starts past the end of the record. Skipping tag and all proceeding tags.");
                    break;
                }
                else if (fieldStart + fieldLength > recordLength)
                {
                    marc.AddWarnings("Directory entry for tag " + tag + " runs past the end of the record.");
                    fieldLength = recordLength - fieldStart;
                }
                string tagData = raw.Substring(fieldStart, fieldLength);

                if (tagData.Substring(tagData.Length - 1, 1) == END_OF_FIELD.ToString())
                {
                    //Get rid of the end of tag character
                    tagData = tagData.Remove(tagData.Length - 1);
                    fieldLength--;
                }
                else
                    marc.AddWarnings("Field for tag " + tag + " does not end with an end of field character.");

                match = Regex.Match(tag, "^\\d+$");
                if (match.Captures.Count > 0 && Convert.ToInt32(tag) < 10)
                    marc.Fields.Add(new ControlField(tag, tagData));
                else
                {
                    List<string> rawSubfields = new List<string>(tagData.Split(SUBFIELD_INDICATOR));
                    string indicators = rawSubfields[0];
                    rawSubfields.RemoveAt(0);

                    char ind1;
                    char ind2;

                    if (indicators.Length != 2)
                    {
                        marc.AddWarnings("Invalid indicator length. Forced indicators to blanks for tag " + tag + ".");
                        ind1 = ind2 = ' ';
                    }
                    else
                    {
                        ind1 = char.ToLower(indicators[0]);

                        if (!DataField.ValidateIndicator(ind1))
                        {
                            ind1 = ' ';
                            marc.AddWarnings("Invalid first indicator. Forced first indicator to blank for tag " + tag + ".");
                        }

                        ind2 = char.ToLower(indicators[1]);

                        if (!DataField.ValidateIndicator(ind2))
                        {
                            ind2 = ' ';
                            marc.AddWarnings("Invalid second indicator. Forced second indicator to blank for tag " + tag + ".");
                        }
                    }

                    //Split the subfield data into subfield name and data pairs
                    List<Subfield> subfieldData = new List<Subfield>();
                    foreach (string subfield in rawSubfields)
                    {
                        if (subfield.Length > 0)
                            subfieldData.Add(new Subfield(subfield[0], subfield.Substring(1)));
                        else
                            marc.AddWarnings("No subfield data found in tag " + tag + ".");
                    }

                    if (subfieldData.Count == 0)
                        marc.AddWarnings("No subfield data found in tag " + tag + ".");

                    marc.Fields.Add(new DataField(tag, subfieldData, ind1, ind2));
                }
            }
            return marc;
        }
        /// <summary>
        /// Writes the specified record.
        /// </summary>
        /// <param name="record">The record.</param>
        public void Write(Record record)
        {
            XDocument xml = record.ToXMLDocument();

            xml.Save(writer);
        }
Beispiel #14
0
        /// <summary>
        /// Makes a deep clone of this instance.
        /// </summary>
        /// <returns></returns>
        public Record Clone()
        {
            Record clone = new Record();

            clone.Leader = this.Leader;
            foreach (string needsCloned in Warnings)
                clone.AddWarnings(needsCloned);

            foreach (Field needsCloned in this.Fields)
                clone.Fields.Add(needsCloned.Clone());

            return clone;
        }