Commit 99a0c461 authored by Martti Käärik's avatar Martti Käärik
Browse files

OpenAPI to TDL converter updates:

- use keyword list from grammar
- use appropriate names for reference and array types
parent 656f5032
Loading
Loading
Loading
Loading
+14 −9
Original line number Diff line number Diff line
@@ -64,21 +64,23 @@ public abstract class AbstractTranslator {
	}

	protected DataType getDataTypeFor(String name) {
		return getTypeFor(cleanName(name), tdlPackage.Literals.DATA_TYPE);
		return getTypeFor(getCleanName(name), tdlPackage.Literals.DATA_TYPE);
	}

	protected SimpleDataType getSimpleDataTypeFor(String name) {
		return getTypeFor(cleanName(name), tdlPackage.Literals.SIMPLE_DATA_TYPE);
		return getTypeFor(getCleanName(name), tdlPackage.Literals.SIMPLE_DATA_TYPE);
	}

	protected EnumDataType getEnumDataTypeFor(String name) {
		return getTypeFor(cleanName(name), tdlPackage.Literals.ENUM_DATA_TYPE);
		return getTypeFor(getCleanName(name), tdlPackage.Literals.ENUM_DATA_TYPE);
	}
	
	protected StructuredDataType getStructuredDataTypeFor(String name) {
		return getTypeFor(cleanName(name), tdlPackage.Literals.STRUCTURED_DATA_TYPE);
		return getTypeFor(getCleanName(name), tdlPackage.Literals.STRUCTURED_DATA_TYPE);
	}

	protected String idStartDigitRegex = "\\A\\d";
	protected String idInvalidCharRegex = "\\W";
	public static String cleanName(String name) {
		//TODO: use keywords filter?
//		List<String> keywords = List.of("Message", "Time", "Type", "type", "name", "instance", "size", "component");
@@ -92,10 +94,13 @@ public abstract class AbstractTranslator {
				.replaceAll("\\.", "_");
		return name;
	}
	public String getCleanName(String name) {
		return cleanName(name);
	}

	@SuppressWarnings("unchecked")
	protected <T extends PackageableElement> T getTypeFor(String name, EClass targetType) {
		String cleanName = cleanName(name);
		String cleanName = getCleanName(name);
		//TODO: move to ASN2TDL specialisation
		TreeMap<String, String> mappings = new TreeMap<>();
		mappings.put("AsnInteger", "Integer");
@@ -119,7 +124,7 @@ public abstract class AbstractTranslator {
		Optional<PackageableElement> optional = generatedPackage.getPackagedElement().stream()
				.filter(e -> 
					targetType.isInstance(e) &&
					e.getName().equals(cleanName(name)))
					e.getName().equals(getCleanName(name)))
				.findFirst();
		T generatedType = null;
		if (optional.isPresent()) {
@@ -145,7 +150,7 @@ public abstract class AbstractTranslator {
	
	@SuppressWarnings("unchecked")
	protected <T extends NamedElement> T getContentWithName(String name, NamedElement container, EClass targetType) {
		String cleanName = cleanName(name);
		String cleanName = getCleanName(name);
		T content = findContentWithName(cleanName, container, targetType);
		if (content == null) {
			content = (T) tdlFactory.eINSTANCE.create(targetType);
@@ -175,7 +180,7 @@ public abstract class AbstractTranslator {
	}
	
	protected void annotateWith(final DataType generatedType, String annotationName) {
		AnnotationType annotationType = getTypeFor(cleanName(annotationName), tdlPackage.Literals.ANNOTATION_TYPE);
		AnnotationType annotationType = getTypeFor(getCleanName(annotationName), tdlPackage.Literals.ANNOTATION_TYPE);
		if (!generatedType.getAnnotation().stream().anyMatch(a->a.getKey()==annotationType)) {
			Annotation annotation = tdlFactory.eINSTANCE.createAnnotation();
			annotation.setKey(annotationType);
@@ -184,7 +189,7 @@ public abstract class AbstractTranslator {
	}

	protected void constrainWith(final DataType generatedType, String constraintName) {
		ConstraintType constraintType = getTypeFor(cleanName(constraintName), tdlPackage.Literals.CONSTRAINT_TYPE);
		ConstraintType constraintType = getTypeFor(getCleanName(constraintName), tdlPackage.Literals.CONSTRAINT_TYPE);
		if (!generatedType.getConstraint().stream().anyMatch(a->a.getType()==constraintType)) {
			Constraint constraint = tdlFactory.eINSTANCE.createConstraint();
			constraint.setType(constraintType);
+11 −0
Original line number Diff line number Diff line
@@ -4,6 +4,7 @@ package org.etsi.mts.tdl.helper;

import java.io.IOException;
import java.util.Collections;
import java.util.Set;

import org.apache.log4j.Level;
import org.apache.log4j.Logger;
@@ -21,6 +22,8 @@ import org.eclipse.ocl.pivot.internal.delegate.OCLSettingDelegateFactory;
import org.eclipse.ocl.pivot.internal.delegate.OCLValidationDelegateFactory;
import org.eclipse.ocl.xtext.completeocl.CompleteOCLStandaloneSetup;
import org.eclipse.ocl.xtext.essentialocl.EssentialOCLStandaloneSetup;
import org.eclipse.xtext.GrammarUtil;
import org.eclipse.xtext.IGrammarAccess;
import org.eclipse.xtext.resource.IResourceServiceProvider;
import org.eclipse.xtext.resource.XtextResourceSet;
import org.eclipse.xtext.serializer.impl.Serializer;
@@ -168,6 +171,14 @@ public class TDLHelper {
		return resourceSet;
	}
	
	public static Set<String> getTdlGrammarKeywords() {
		injector = new TDLtxStandaloneSetup().createInjectorAndDoEMFRegistration();
		IGrammarAccess grammarAccess = injector.getInstance(IGrammarAccess.class);
		if (grammarAccess != null)
			return GrammarUtil.getAllKeywords(grammarAccess.getGrammar());
		return Collections.EMPTY_SET;
	}

	/**
	 * Reset the shared resourceSet.
	 */
+91 −45
Original line number Diff line number Diff line
package org.etsi.mts.tdl.openapi2tdl.next;

import java.io.File;
import java.util.Hashtable;
import java.util.Map;
import java.util.Set;

import org.eclipse.emf.ecore.resource.Resource;
import org.etsi.mts.tdl.CollectionDataType;
import org.etsi.mts.tdl.DataElementMapping;
import org.etsi.mts.tdl.DataType;
import org.etsi.mts.tdl.Member;
import org.etsi.mts.tdl.StructuredDataType;
import org.etsi.mts.tdl.tdlPackage;
import org.etsi.mts.tdl.helper.TDLHelper;
import org.etsi.mts.tdl.transform.AbstractTranslator;
import org.openapitools.codegen.utils.ModelUtils;

@@ -17,12 +22,16 @@ import io.swagger.v3.oas.models.media.Schema;
import io.swagger.v3.parser.core.models.ParseOptions;
import io.swagger.v3.parser.util.InlineModelResolver;


public class OpenAPI2TDLTranslatorNext extends AbstractTranslator {

	// TODO: cleanup and prepare for release
	private OpenAPI model;

	private boolean isXtext = false;
	private Set<String> xtextKyewords;

	private Map<String, String> nameReplacements = new Hashtable();

	public void translate(String filename) throws Exception {
		translate(filename, sourceMappingTag, targetMappingTag);
	}
@@ -53,6 +62,24 @@ public class OpenAPI2TDLTranslatorNext extends AbstractTranslator {

	}
	
	@Override
	public void setTargetResource(Resource targetResource) {
		super.setTargetResource(targetResource);
		
		Class resourceClass = targetResource.getClass();
		do {
			// Flaky
			if (resourceClass.getSimpleName().equals("XtextResource")) {
				isXtext = true;
				break;
			}
			resourceClass = resourceClass.getSuperclass();
		} while (resourceClass != null);
		
		if (isXtext)
			xtextKyewords = TDLHelper.getTdlGrammarKeywords();
	}

	private void addMapping(Schema<?> schema, DataType dataType, String sourceMappingTag, String targetMappingTag) {
		DataElementMapping sourceMapping = addDataElementMapping("#/components/schemas/"+schema.getName()+"", dataType, sourceMappingTag);

@@ -92,7 +119,7 @@ public class OpenAPI2TDLTranslatorNext extends AbstractTranslator {

	private DataType translateObject(Schema<?> schema, String name) {
		StructuredDataType dataType = getStructuredDataTypeFor(name);
		if (schema.getProperties()==null) {
		if (schema.getProperties() == null || !dataType.getMember().isEmpty()) {
			return dataType;
		}
		for (Object propertyName : schema.getProperties().keySet()) {
@@ -117,19 +144,38 @@ public class OpenAPI2TDLTranslatorNext extends AbstractTranslator {

	private DataType translateArray(Schema<?> schema, String name) {
		Schema<?> itemsSchema = schema.getItems();
		CollectionDataType collectionType = getTypeFor(name, tdlPackage.Literals.COLLECTION_DATA_TYPE);
		String reference = itemsSchema.get$ref();
		DataType itemType;
		if (reference != null) {
			Schema<?> referencedSchema = ModelUtils.getReferencedSchema(model, itemsSchema);
			DataType itemType = translate(referencedSchema, name);
			collectionType.setItemType(itemType);
			referencedSchema.setName(ModelUtils.getSimpleRef(reference));
			itemType = translate(referencedSchema, "");
		} else {
			DataType itemType = translate(itemsSchema, name);
			collectionType.setItemType(itemType);
			itemType = translate(itemsSchema, name);
		}
		CollectionDataType collectionType = getTypeFor(itemType.getName() + "_collection",
				tdlPackage.Literals.COLLECTION_DATA_TYPE);
		collectionType.setItemType(itemType);
		return collectionType;
	}

	public String getCleanName(String name) {
		String replacement = nameReplacements.get(name);
		if (replacement != null)
			return replacement;
		replacement = name;
		if (isXtext) {
			if (replacement.matches(idStartDigitRegex))
				replacement = "_" + replacement;
			replacement = replacement.replaceAll(idInvalidCharRegex, "_");
			if (xtextKyewords.contains(replacement)) {
				replacement = "^" + replacement;
			}
		}
		// TODO check for duplicates
		nameReplacements.put(name, replacement);
		return replacement;
	}

	/**
     * Helper method for parsing specs into an intermediary OpenAPI structure for pre-processing.