| package org.onosproject.yangtool; |
| |
| import com.google.common.io.Files; |
| import org.apache.commons.configuration.ConfigurationException; |
| import org.apache.commons.configuration.XMLConfiguration; |
| import org.apache.commons.io.FileUtils; |
| import org.apache.commons.io.IOUtils; |
| import org.onlab.util.Tools; |
| |
| import java.io.BufferedReader; |
| import java.io.File; |
| import java.io.FileInputStream; |
| import java.io.IOException; |
| import java.io.InputStream; |
| import java.io.InputStreamReader; |
| import java.io.PrintWriter; |
| import java.nio.charset.Charset; |
| import java.util.ArrayList; |
| import java.util.Arrays; |
| import java.util.List; |
| import java.util.stream.Collectors; |
| |
| /** |
| * Class that takes in input two paths, one to the yang file and one where |
| * to generate the interface, and a yang container name, generates the sources |
| * through OpenDaylight code generator plugin from yang, and modifies |
| * them accordingly to the needs of the ONOS behavior system. |
| */ |
| public class YangLoader { |
| /** |
| * Public method to take a yang file from the input folder and generate classes |
| * to the output folder. |
| * @param inputFolder forlder with the yang files |
| * @param completeOuputFolder folder where to put the desired classes |
| * @throws IOException |
| * @throws ConfigurationException |
| * @throws InterruptedException |
| */ |
| public void generateBehaviourInterface(String inputFolder, |
| String completeOuputFolder) |
| throws IOException, ConfigurationException, InterruptedException { |
| File projectDir = createTemporaryProject(inputFolder); |
| List<String> containerNames = findContainerName( |
| new File(projectDir.getAbsolutePath() + "/src")); |
| System.out.println("Containers " + containerNames); |
| generateJava(projectDir); |
| //modifyClasses(containerName, projectDir, completeInterfaceOuputFolder); |
| copyFiles(new File(projectDir.getAbsolutePath() + "/dst"), |
| new File(completeOuputFolder)); |
| //System.out.println("Sources in " + completeOuputFolder); |
| |
| } |
| |
| private List<String> findContainerName(File scrDir) { |
| List<String> allContainers = new ArrayList<>(); |
| Arrays.asList(scrDir.listFiles()).stream().forEach(f -> { |
| try { |
| FileUtils.readLines(f).stream() |
| .filter(line -> line.matches("(.*)container(.*)\\{")) |
| .collect(Collectors.toList()).forEach(s -> { |
| s = s.replace("container", ""); |
| s = s.replace("{", ""); |
| allContainers.add(s.trim()); |
| }); |
| |
| } catch (IOException e) { |
| throw new RuntimeException(e); |
| } |
| }); |
| return allContainers; |
| } |
| |
| private File createTemporaryProject(String inputFolder) throws IOException, |
| ConfigurationException { |
| File tempDir = Files.createTempDir(); |
| File scrDir = new File(tempDir, "src"); |
| scrDir.mkdir(); |
| copyFiles(new File(inputFolder), scrDir); |
| createPomFile(tempDir, scrDir); |
| return tempDir; |
| |
| } |
| |
| private void copyFiles(File inputFolder, File scrDir) throws IOException { |
| Tools.copyDirectory(inputFolder, scrDir); |
| } |
| |
| private void createPomFile(File tempDir, File scrDir) throws ConfigurationException { |
| File pom = new File(tempDir, "pom.xml"); |
| File dstDir = new File(tempDir, "dst"); |
| dstDir.mkdir(); |
| XMLConfiguration cfg = new XMLConfiguration(); |
| cfg.load(getClass().getResourceAsStream("/pom-template.xml")); |
| cfg.setProperty("build.plugins.plugin.executions.execution." + |
| "configuration.yangFilesRootDir", scrDir.getPath()); |
| cfg.setProperty("build.plugins.plugin.executions." + |
| "execution.configuration.codeGenerators." + |
| "generator.outputBaseDir", dstDir.getPath()); |
| cfg.save(pom); |
| } |
| |
| private void generateJava(File projectDir) |
| throws IOException, InterruptedException { |
| Runtime rt = Runtime.getRuntime(); |
| Process pr = rt.exec("mvn generate-sources", null, projectDir); |
| String s = IOUtils.toString(pr.getInputStream(), "UTF-8"); |
| if (pr.waitFor() == 0) { |
| if (s.contains("[WARNING]")) { |
| System.out.println("Sources not generated, warning log: \n" + s); |
| } else { |
| System.out.println("Sources generated"); |
| } |
| } else { |
| System.out.println("Sources not generated. " + s + |
| " \nError " + pr.getInputStream().read()); |
| } |
| } |
| |
| //parsing classes part, for now is not used. |
| private void modifyClasses(String containerName, File projectDir, |
| String pathToNewInterface) throws IOException { |
| String odlInterfacepath = getPathWithFileName(containerName, projectDir.getPath()); |
| odlInterfacepath = odlInterfacepath + "/"; |
| parseClass(odlInterfacepath, pathToNewInterface, containerName); |
| System.out.println("ONOS behaviour interface generated " + |
| "correctly at " + pathToNewInterface); |
| } |
| |
| private String getPathWithFileName(String filename, String pathToGenerated) { |
| File[] directories = new File(pathToGenerated).listFiles(File::isDirectory); |
| while (directories.length != 0) { |
| pathToGenerated = pathToGenerated + "/" + directories[0].getName(); |
| directories = new File(pathToGenerated).listFiles(File::isDirectory); |
| } |
| File dir = new File(pathToGenerated); |
| File behaviour = (File) Arrays.asList(dir.listFiles()).stream() |
| .filter(f -> f.getName().equals(filename)).toArray()[0]; |
| return behaviour.getParentFile().getAbsolutePath(); |
| } |
| |
| private void parseClass(String filePath, String pathToNewInterface, |
| String filename) throws IOException { |
| InputStream fis = null; |
| String newFile = "package org.onosproject.net.behaviour;\n" + |
| "import org.onosproject.net.driver.HandlerBehaviour;\n"; |
| fis = new FileInputStream(filePath + filename); |
| InputStreamReader isr = new InputStreamReader(fis, Charset.forName("UTF-8")); |
| BufferedReader br = new BufferedReader(isr); |
| String line; |
| while ((line = br.readLine()) != null) { |
| if (!line.contains("org.opendaylight.")) { |
| if (line.contains("ChildOf")) { |
| newFile = newFile + "HandlerBehaviour\n"; |
| } else { |
| newFile = newFile + line + "\n"; |
| } |
| } |
| } |
| PrintWriter out = new PrintWriter(pathToNewInterface + |
| filename.replace(".java", "") |
| + "Interface.java"); |
| out.print(newFile); |
| out.flush(); |
| } |
| |
| |
| } |