stevedlawrence commented on a change in pull request #394: URL: https://github.com/apache/incubator-daffodil/pull/394#discussion_r453973431
########## File path: daffodil-core/src/main/scala/org/apache/daffodil/dsom/walker/RecordWalker.scala ########## @@ -0,0 +1,309 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.daffodil.dsom.walker + +import java.io.File +import java.util + +import org.apache.daffodil.dsom.{Choice, ComplexTypeBase, ElementBase, GroupRef, Root, Sequence, SimpleTypeBase, Term} +import org.apache.nifi.serialization.SimpleRecordSchema +import org.apache.nifi.serialization.record.{DataType, RecordField, RecordFieldType, RecordSchema, SchemaIdentifier} +import org.apache.nifi.serialization.record.`type`.RecordDataType +import scala.collection.mutable.ListBuffer + +/** + * Direct subclass of the NIFI RecordField. NIFI doesn't have "Optional" fields, so + * eventually this will either be removed from the Schema if an Infoset doesn't have the field, + * or it will become a regular RecordField if it does. + * @param fieldName the name for the RecordField + * @param dataType the NIFI DataType of this RecordField + */ +class OptionalRecordField(fieldName: String, dataType: DataType) + extends RecordField(fieldName, dataType) { + // this is the easiest way to construct it; essentially a "copy constructor" except to denote + // that we want to treat it as this special optional subclass. + def this(recordField: RecordField) = this(recordField.getFieldName, recordField.getDataType) + override def equals(obj: Any): Boolean = + obj match { + case _: OptionalRecordField => super.equals(obj) + case _ => false + } + override def hashCode(): Int = 31 * super.hashCode() + 1 + override def toString: String = "Optional" + super.toString +} + +/** + * Concrete implementation of the AbstractDSOMWalker abstract class. + * This class produces a NIFI RecordSchema that is intended to match the original DFDL file. + * + * The RecordSchema is built in 3 primary stages: + * 1) A tree of SchemaNodes is created as the DFDL file is walked; this walk is performed + * through the various event handlers defined in the parent abstract class. + * 2) The tree of SchemaNodes undergoes some post-processing, mainly to remove redundant Record wrappers. + * 3) The tree of SchemaNodes is converted into a RecordSchema; it is walked recursively within this class. + * @param schemaFile an input DFDL Schema file to parse + */ +class RecordWalker(schemaFile: File) extends AbstractDSOMWalker[RecordSchema](schemaFile) { Review comment: In theory, the only thing that needs to be in the Daffodil codebase is the API, which is essentially the AbstractDSOMWalker and all the Views traits. Nothing depending on NiFi should go in daffodil-core because that means core depends on NiFi and thus anyone using Daffodil now needs a NiFi jar--the use of Daffodli shouldn't depend on NiFi. I don't think it really matters where the AbstractDSOMWalker and View traits go. They can probably just stay in core. Note that they can't go in the japi/sapi directories. This is because daffodilxXapi currently depends on daffodil-core (xapi is essentially a basic wrapper around core). If these AbstractDSOMWalker and View traits were in the daffodil-xapi, then daffodil-core would then depend on daffodil-xapi, so we'd have a circular dependency. So the AbstractDSOMWalker and View traits either stay in daffodil-core or in a new subproject. Since we are considering this experiemental, maybe it makes sense to keep it in core, and when we finalize an API and move it from experimental, we can move it to a separate dir where we can generate public java/scaladocs? I guess this is essentially what we've done with daffodil-udf. I consider it a public API so it makes sense to get it's own directory where we can generate docs for it. So where does everything go that uses NiFi? It should probably all stick together in one place. Perhaps that place right now is the nifi-daffodil repo, just to make it very obvious what is NiFi and what is Daffodil, and to highlight what changes are Daffodil API additions and what are NiFi usages of this API? Once that's finalized and the nifi-daffodil repo is in a stable state and the experimental API is considered sufficient, it then becomes pretty trivial to either merge that into Nifi if they are willing to accept it, or merge it into a new Daffodli "integrations" directory for it to live. Or it could just remain separate--though I'd prefer it get merged somewhere. ---------------------------------------------------------------- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. For queries about this service, please contact Infrastructure at: [email protected]
