All Downloads are FREE. Search and download functionalities are using the official Maven repository.

smithy4s.codegen.internals.SmithyResources.scala Maven / Gradle / Ivy

/*
 *  Copyright 2021-2024 Disney Streaming
 *
 *  Licensed under the Tomorrow Open Source Technology License, Version 1.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *     https://disneystreaming.github.io/TOST-1.0.txt
 *
 *  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 smithy4s.codegen.internals

import os.RelPath
import smithy4s.codegen.BuildInfo
import smithy4s.codegen.CodegenEntry

/**
  * This construct aims at adding metadata information to the classpath to let Smithy4s
  * know about code that may have been generated in upstream modules.
  *
  * A "smithy4sGenerated" metadata holds a list of all namespaces that will have already
  * been generated by smithy4s.
  */
private[smithy4s] object SmithyResources {

  def produce(
      resourceOutputFolder: os.Path,
      specs: List[os.Path],
      namespaces: List[String]
  ): List[CodegenEntry] = {

    val localSmithyFiles = specs.flatMap { spec =>
      if (os.isDir(spec))
        os.walk(spec).filter(f => Set("smithy", "json").contains(f.ext))
      else if (Set("smithy", "json").contains(spec.ext)) List(spec)
      else Nil
    }

    val smithyFolder = resourceOutputFolder / "META-INF" / "smithy"
    val trackingFile = smithyFolder / s"smithy4s.tracking.smithy"

    val smithy4sVersion = BuildInfo.version
    val nsString = namespaces.map(ns => s""""$ns"""").mkString(", ")
    val content = s"""|$$version: "2.0"
                      |
                      |metadata smithy4sGenerated = [{smithy4sVersion: "$smithy4sVersion", namespaces: [$nsString]}]
                      |""".stripMargin
    val trackingFileEntry = CodegenEntry.FromMemory(trackingFile, content)

    val metadataFile = smithyFolder / "manifest"
    val metadataFileRelPaths =
      (trackingFile :: localSmithyFiles).flatMap {
        case f if os.isDir(f) =>
          os.walk(f).filter(os.isFile(_)).map(_.relativeTo(f))
        case f => RelPath(f.last) :: Nil
      }.distinct

    val metadataFileEntry = CodegenEntry.FromMemory(
      metadataFile,
      metadataFileRelPaths.mkString(System.lineSeparator())
    )

    val localSmithyFilesEntries = localSmithyFiles
      .map { path =>
        CodegenEntry.FromDisk(smithyFolder / path.last, path)
      }

    localSmithyFilesEntries :+ metadataFileEntry :+ trackingFileEntry
  }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy