1   /* Copyright 2024-2025 The Johns Hopkins University Applied Physics Laboratory
2    * Licensed to CS GROUP (CS) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * CS licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *   http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.orekit.files.iirv;
18  
19  import org.orekit.errors.OrekitIllegalArgumentException;
20  import org.orekit.errors.OrekitInternalError;
21  import org.orekit.errors.OrekitMessages;
22  import org.orekit.files.general.EphemerisFile;
23  import org.orekit.files.general.EphemerisFileWriter;
24  import org.orekit.utils.TimeStampedPVCoordinates;
25  
26  import java.io.IOException;
27  import java.util.List;
28  
29  /**
30   * An {@link EphemerisFileWriter} for generating {@link IIRVMessage IIRV} files.
31   * <p>
32   * This class uses an inputted {@link IIRVBuilder} object to define the message metadata
33   * values that comprise an IIRV message.
34   * <p>
35   * This class can be used to write a list of {@link TimeStampedPVCoordinates} as an IIRV file as follows:
36   * <pre>{@code
37   *
38   * // 1. Create an IIRVBuilder class to define the spacecraft/mission metadata values
39   * IIRVBuilder iirvBuilder = new IIRVBuilder(TimeScalesFactory.getUTC());
40   * iirvBuilder.setSupportIdCode(1221);
41   * iirvBuilder.setDragCoefficient(2.2);
42   * iirvBuilder.setOriginIdentification(OriginIdentificationTerm.GSFC);
43   * iirvBuilder.setRoutingIndicator("MANY");
44   * // ... (additional fields here)
45   *
46   * // 2. Create an IIRVFileWriter with the builder object
47   * IIRVFileWriter writer = new IIRVFileWriter(iirvBuilder, IIRVMessage.IncludeMessageMetadata.ALL_VECTORS);
48   *
49   * // 3. Generate an IIRVEphemerisFile containing the ephemeris data
50   * IIRVEphemerisFile iirvFile = iirvBuilder.buildEphemerisFile(coordinates);
51   *
52   * // 4. Write to disk. Recommendation: embed the start year in the filename (year does not appear in the IIRV itself)
53   * String testFilename = "TestSatellite" + "_" +
54   *      iirvFile.getStartYear() + "_" +
55   *      iirvFile.getIIRV().get(0).getDayOfYear().toEncodedString() + "_" +
56   *      iirvFile.getIIRV().get(0).getVectorEpoch().toEncodedString() + ".iirv";
57   * writer.write(testFilename, iirvFile);
58   *  }
59   * </pre>
60   *
61   * @author Nick LaFarge
62   * @see StreamingIIRVFileWriter
63   * @see IIRVMessage
64   * @since 13.0
65   */
66  public class IIRVFileWriter implements EphemerisFileWriter {
67  
68      /** Builder class for IIRV. */
69      private final IIRVBuilder builder;
70  
71      /** Setting for when message metadata terms appear in the created IIRV message. */
72      private final IIRVMessage.IncludeMessageMetadata includeMessageMetadataSetting;
73  
74      /**
75       * Constructor.
76       *
77       * @param builder                       Builder class for IIRV
78       * @param includeMessageMetadataSetting Setting for when message metadata terms appear in the created IIRV message
79       */
80      public IIRVFileWriter(final IIRVBuilder builder, final IIRVMessage.IncludeMessageMetadata includeMessageMetadataSetting) {
81          this.builder = builder;
82          this.includeMessageMetadataSetting = includeMessageMetadataSetting;
83      }
84  
85      /** {@inheritDoc} */
86      @Override
87      public <C extends TimeStampedPVCoordinates, S extends EphemerisFile.EphemerisSegment<C>> void write(final Appendable writer, final EphemerisFile<C, S> ephemerisFile) throws IOException {
88  
89          if (writer == null) {
90              throw new OrekitIllegalArgumentException(OrekitMessages.NULL_ARGUMENT, "writer");
91          }
92  
93          if (ephemerisFile == null) {
94              return;
95          }
96          final EphemerisFile.SatelliteEphemeris<C, S> satEphem = ephemerisFile.getSatellites().get(builder.getSatelliteID());
97  
98          final List<S> segments = satEphem.getSegments();
99          if (segments.size() > 1) {
100             // This should never happen
101             throw new OrekitInternalError(null);
102         }
103 
104         final StreamingIIRVFileWriter streamingWriter = new StreamingIIRVFileWriter(writer, includeMessageMetadataSetting);
105         final IIRVMessage iirvMessage = builder.buildIIRVMessage(segments.get(0).getCoordinates());
106         streamingWriter.writeIIRVMessage(iirvMessage);
107     }
108 }