Remove protobuf stdlib module (#1976)
This commit is contained in:
1 parent
155fc5a867
commit
2d7a368b48
25 files changed
+4
-1567
No files matched your search
@@ -77,7 +77,6 @@ endif::[]
|
|||||||
:uri-stdlib-netModule: {uri-pkl-stdlib-docs}/net
|
:uri-stdlib-netModule: {uri-pkl-stdlib-docs}/net
|
||||||
:uri-stdlib-net-Url: {uri-stdlib-netModule}/Url
|
:uri-stdlib-net-Url: {uri-stdlib-netModule}/Url
|
||||||
:uri-stdlib-xmlModule: {uri-pkl-stdlib-docs}/xml
|
:uri-stdlib-xmlModule: {uri-pkl-stdlib-docs}/xml
|
||||||
:uri-stdlib-protobufModule: {uri-pkl-stdlib-docs}/protobuf
|
|
||||||
:uri-stdlib-pklbinaryModule: {uri-pkl-stdlib-docs}/pklbinary
|
:uri-stdlib-pklbinaryModule: {uri-pkl-stdlib-docs}/pklbinary
|
||||||
:uri-stdlib-yamlModule: {uri-pkl-stdlib-docs}/yaml
|
:uri-stdlib-yamlModule: {uri-pkl-stdlib-docs}/yaml
|
||||||
:uri-stdlib-YamlParser: {uri-stdlib-yamlModule}/Parser
|
:uri-stdlib-YamlParser: {uri-stdlib-yamlModule}/Parser
|
||||||
|
|||||||
@@ -2752,7 +2752,6 @@ The standard library provides these renderers:
|
|||||||
* link:{uri-stdlib-baseModule}/PcfRenderer[PcfRenderer]
|
* link:{uri-stdlib-baseModule}/PcfRenderer[PcfRenderer]
|
||||||
* link:{uri-stdlib-baseModule}/PListRenderer[PListRenderer]
|
* link:{uri-stdlib-baseModule}/PListRenderer[PListRenderer]
|
||||||
* link:{uri-stdlib-baseModule}/PropertiesRenderer[PropertiesRenderer]
|
* link:{uri-stdlib-baseModule}/PropertiesRenderer[PropertiesRenderer]
|
||||||
* link:{uri-stdlib-protobufModule}/Renderer[protobuf.Renderer]
|
|
||||||
* link:{uri-stdlib-xmlModule}/Renderer[xml.Renderer]
|
* link:{uri-stdlib-xmlModule}/Renderer[xml.Renderer]
|
||||||
* link:{uri-stdlib-baseModule}/YamlRenderer[YamlRenderer]
|
* link:{uri-stdlib-baseModule}/YamlRenderer[YamlRenderer]
|
||||||
|
|
||||||
|
|||||||
@@ -307,7 +307,6 @@ The default output renderer for a module supports the following formats:
|
|||||||
* `pcf`
|
* `pcf`
|
||||||
* `plist`
|
* `plist`
|
||||||
* `properties`
|
* `properties`
|
||||||
* `textproto` (deprecated in Pkl 0.33)
|
|
||||||
* `xml`
|
* `xml`
|
||||||
* `yaml`
|
* `yaml`
|
||||||
|
|
||||||
|
|||||||
@@ -152,7 +152,6 @@ The default output renderer for a module supports the following formats:
|
|||||||
* `"pcf"`
|
* `"pcf"`
|
||||||
* `"plist"`
|
* `"plist"`
|
||||||
* `"properties"`
|
* `"properties"`
|
||||||
* `"textproto"` (deprecated in Pkl 0.33)
|
|
||||||
* `"xml"`
|
* `"xml"`
|
||||||
* `"yaml"`
|
* `"yaml"`
|
||||||
====
|
====
|
||||||
|
|||||||
@@ -52,7 +52,6 @@ data class CliEvaluatorOptions(
|
|||||||
* - `"pcf"` (default)
|
* - `"pcf"` (default)
|
||||||
* - `"plist"`
|
* - `"plist"`
|
||||||
* - `"properties"`
|
* - `"properties"`
|
||||||
* - `"textproto"` (deprecated in Pkl 0.33)
|
|
||||||
* - `"xml"`
|
* - `"xml"`
|
||||||
* - `"yaml"`
|
* - `"yaml"`
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -709,8 +709,7 @@ result = someLib.x
|
|||||||
assertThat(output).isEqualTo("x: 1\n---\nx: 3\n")
|
assertThat(output).isEqualTo("x: 1\n---\nx: 3\n")
|
||||||
}
|
}
|
||||||
|
|
||||||
// prototext can't render `Dynamic`.
|
@EnumSource
|
||||||
@EnumSource(names = ["TEXTPROTO"], mode = EnumSource.Mode.EXCLUDE)
|
|
||||||
@ParameterizedTest(name = "{0} console output ends with newline")
|
@ParameterizedTest(name = "{0} console output ends with newline")
|
||||||
fun `console output ends with newline`(outputFormat: OutputFormat) {
|
fun `console output ends with newline`(outputFormat: OutputFormat) {
|
||||||
val sourceFiles = listOf(writePklFile("test0.pkl", "foo = 0\nbar=\"Baz\""))
|
val sourceFiles = listOf(writePklFile("test0.pkl", "foo = 0\nbar=\"Baz\""))
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright © 2024 Apple Inc. and the Pkl project authors. All rights reserved.
|
* Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -22,7 +22,6 @@ public enum OutputFormat {
|
|||||||
PCF("pcf"),
|
PCF("pcf"),
|
||||||
PROPERTIES("properties"),
|
PROPERTIES("properties"),
|
||||||
PLIST("plist"),
|
PLIST("plist"),
|
||||||
TEXTPROTO("textproto"),
|
|
||||||
XML("xml"),
|
XML("xml"),
|
||||||
YAML("yaml");
|
YAML("yaml");
|
||||||
|
|
||||||
|
|||||||
@@ -1,663 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved.
|
|
||||||
*
|
|
||||||
* Licensed 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
|
|
||||||
*
|
|
||||||
* https://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.pkl.core.stdlib.protobuf;
|
|
||||||
|
|
||||||
import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary;
|
|
||||||
import com.oracle.truffle.api.dsl.Cached;
|
|
||||||
import com.oracle.truffle.api.dsl.Specialization;
|
|
||||||
import com.oracle.truffle.api.nodes.IndirectCallNode;
|
|
||||||
import java.util.ArrayDeque;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.Deque;
|
|
||||||
import java.util.Optional;
|
|
||||||
import org.jspecify.annotations.Nullable;
|
|
||||||
import org.pkl.core.DurationUnit;
|
|
||||||
import org.pkl.core.ast.member.ClassProperty;
|
|
||||||
import org.pkl.core.ast.member.PropertyTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.BooleanTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.IntSlotTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.IntTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.ListTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.ListingOrMappingTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.ListingTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.MapTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.MappingTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.NonFinalClassTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.NullableTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.ObjectSlotTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.SetTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.StringLiteralTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.StringTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.TypeAliasTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.UnionOfStringLiteralsTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.UnionTypeNode;
|
|
||||||
import org.pkl.core.ast.type.TypeNode.UnionTypeNodeExploded;
|
|
||||||
import org.pkl.core.ast.type.VmTypeMismatchException;
|
|
||||||
import org.pkl.core.runtime.Identifier;
|
|
||||||
import org.pkl.core.runtime.VmBytes;
|
|
||||||
import org.pkl.core.runtime.VmClass;
|
|
||||||
import org.pkl.core.runtime.VmDataSize;
|
|
||||||
import org.pkl.core.runtime.VmDuration;
|
|
||||||
import org.pkl.core.runtime.VmDynamic;
|
|
||||||
import org.pkl.core.runtime.VmExceptionBuilder;
|
|
||||||
import org.pkl.core.runtime.VmIntSeq;
|
|
||||||
import org.pkl.core.runtime.VmLanguage;
|
|
||||||
import org.pkl.core.runtime.VmList;
|
|
||||||
import org.pkl.core.runtime.VmListing;
|
|
||||||
import org.pkl.core.runtime.VmMap;
|
|
||||||
import org.pkl.core.runtime.VmMapping;
|
|
||||||
import org.pkl.core.runtime.VmNull;
|
|
||||||
import org.pkl.core.runtime.VmPair;
|
|
||||||
import org.pkl.core.runtime.VmReference;
|
|
||||||
import org.pkl.core.runtime.VmRegex;
|
|
||||||
import org.pkl.core.runtime.VmSet;
|
|
||||||
import org.pkl.core.runtime.VmType;
|
|
||||||
import org.pkl.core.runtime.VmTyped;
|
|
||||||
import org.pkl.core.runtime.VmUtils;
|
|
||||||
import org.pkl.core.runtime.VmValue;
|
|
||||||
import org.pkl.core.stdlib.AbstractStringRenderer;
|
|
||||||
import org.pkl.core.stdlib.ExternalMethod1Node;
|
|
||||||
import org.pkl.core.stdlib.PklConverter;
|
|
||||||
import org.pkl.core.util.ArrayCharEscaper;
|
|
||||||
import org.pkl.core.util.json.JsonEscaper;
|
|
||||||
|
|
||||||
public final class RendererNodes {
|
|
||||||
// Defined here because only relevant to this class.
|
|
||||||
private static final Identifier SECONDS = Identifier.get("seconds");
|
|
||||||
private static final Identifier NANOS = Identifier.get("nanos");
|
|
||||||
|
|
||||||
private static final ArrayCharEscaper fieldNameEscaper =
|
|
||||||
ArrayCharEscaper.builder().withEscape('.', "_").withEscape('#', "_").build();
|
|
||||||
|
|
||||||
private static final StringTypeNode STRING_TYPE =
|
|
||||||
new StringTypeNode(VmUtils.unavailableSourceSection());
|
|
||||||
private static final IntTypeNode INT_TYPE = new IntTypeNode(VmUtils.unavailableSourceSection());
|
|
||||||
|
|
||||||
private RendererNodes() {}
|
|
||||||
|
|
||||||
public abstract static class renderDocument extends ExternalMethod1Node {
|
|
||||||
@Specialization
|
|
||||||
@TruffleBoundary
|
|
||||||
protected String eval(
|
|
||||||
VmTyped self, Object value, @Cached("create()") IndirectCallNode callNode) {
|
|
||||||
var builder = new StringBuilder();
|
|
||||||
createRenderer(self, builder, callNode).renderDocument(value);
|
|
||||||
return builder.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public abstract static class renderValue extends ExternalMethod1Node {
|
|
||||||
@Specialization
|
|
||||||
@TruffleBoundary
|
|
||||||
protected String eval(
|
|
||||||
VmTyped self, Object value, @Cached("create()") IndirectCallNode callNode) {
|
|
||||||
var builder = new StringBuilder();
|
|
||||||
createRenderer(self, builder, callNode).renderValue(value);
|
|
||||||
return builder.toString();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public abstract static class renderType extends ExternalMethod1Node {
|
|
||||||
@SuppressWarnings("unused")
|
|
||||||
@Specialization
|
|
||||||
protected String eval(VmTyped self, Object value) {
|
|
||||||
return renderType(value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@TruffleBoundary
|
|
||||||
private static String renderType(Object value) {
|
|
||||||
var clazz =
|
|
||||||
value instanceof VmValue vmValue
|
|
||||||
? vmValue.getVmClass()
|
|
||||||
: value instanceof TypeNode typeNode
|
|
||||||
? typeNode.getType().getVmClass()
|
|
||||||
: value.getClass();
|
|
||||||
if (clazz == null) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotResolveTypeForProtobuf")
|
|
||||||
.withProgramValue("Value", value)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
var name =
|
|
||||||
clazz instanceof VmClass vmClass
|
|
||||||
? vmClass.getSimpleName()
|
|
||||||
: ((Class<?>) clazz).getSimpleName();
|
|
||||||
|
|
||||||
return fieldNameEscaper.escape(name);
|
|
||||||
}
|
|
||||||
|
|
||||||
@TruffleBoundary
|
|
||||||
private static ProtobufRenderer createRenderer(
|
|
||||||
VmTyped self, StringBuilder builder, IndirectCallNode callNode) {
|
|
||||||
var indent = (String) VmUtils.readMember(self, Identifier.INDENT, callNode);
|
|
||||||
return new ProtobufRenderer(builder, indent, PklConverter.fromRenderer(self, callNode));
|
|
||||||
}
|
|
||||||
|
|
||||||
private static final class ProtobufRenderer extends AbstractStringRenderer {
|
|
||||||
private final Deque<Identifier> propertyPath = new ArrayDeque<>();
|
|
||||||
private final Deque<Boolean> wrapperRequirement = new ArrayDeque<>();
|
|
||||||
private final JsonEscaper jsonEscaper = new JsonEscaper(false);
|
|
||||||
|
|
||||||
private @Nullable TypeNode collectionType = null;
|
|
||||||
|
|
||||||
public ProtobufRenderer(StringBuilder builder, String indent, PklConverter converter) {
|
|
||||||
super("Protobuf", builder, indent, converter, true, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitDocument(Object value) {
|
|
||||||
visit(value);
|
|
||||||
startNewLine();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitTopLevelValue(Object value) {
|
|
||||||
if (value instanceof VmValue && !(value instanceof VmTyped || value instanceof VmDuration)) {
|
|
||||||
var name = value.getClass().getSimpleName();
|
|
||||||
if (name.startsWith("Vm")) {
|
|
||||||
name = name.substring(2);
|
|
||||||
}
|
|
||||||
throw new VmExceptionBuilder().evalError("invalidProtobufTopLevelValue", name).build();
|
|
||||||
}
|
|
||||||
assert propertyPath.isEmpty() && wrapperRequirement.isEmpty() : "Corrupted traversal stack.";
|
|
||||||
wrapperRequirement.push(false);
|
|
||||||
visit(value);
|
|
||||||
var wrap = wrapperRequirement.pop();
|
|
||||||
assert !wrap && propertyPath.isEmpty() && wrapperRequirement.isEmpty()
|
|
||||||
: "Corrupted traversal stack.";
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitRenderDirective(VmTyped value) {
|
|
||||||
writePropertyName();
|
|
||||||
// append verbatim
|
|
||||||
builder.append(VmUtils.readTextProperty(value));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startDynamic(VmDynamic value) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderTypeAddConverter", "Dynamic", "Protobuf")
|
|
||||||
.withProgramValue("Value", value)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endDynamic(VmDynamic value, boolean isEmpty) {}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startTyped(VmTyped value) {
|
|
||||||
wrapperRequirement.push(false);
|
|
||||||
if (!propertyPath.isEmpty()) {
|
|
||||||
writePropertyName();
|
|
||||||
startMessage();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endTyped(VmTyped value, boolean isEmpty) {
|
|
||||||
var popped = wrapperRequirement.pop();
|
|
||||||
assert !popped : "Corrupted traversal stack.";
|
|
||||||
if (!propertyPath.isEmpty()) {
|
|
||||||
endMessage();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startListing(VmListing value) {
|
|
||||||
startWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endListing(VmListing value, boolean isEmpty) {
|
|
||||||
endWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startMapping(VmMapping value) {
|
|
||||||
startMaplike();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endMapping(VmMapping value, boolean isEmpty) {
|
|
||||||
endMaplike();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startMaplike() {
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
writePropertyName();
|
|
||||||
propertyPath.push(Identifier.IT);
|
|
||||||
startMessage();
|
|
||||||
}
|
|
||||||
wrapperRequirement.push(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void endMaplike() {
|
|
||||||
wrapperRequirement.pop();
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
endMessage();
|
|
||||||
var popped = propertyPath.pop();
|
|
||||||
assert popped == Identifier.IT : "Corrupted traversal stack.";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startList(VmList value) {
|
|
||||||
startWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endList(VmList value) {
|
|
||||||
endWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startSet(VmSet value) {
|
|
||||||
startWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endSet(VmSet value) {
|
|
||||||
endWrapper();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void startMap(VmMap value) {
|
|
||||||
startMaplike();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void endMap(VmMap value) {
|
|
||||||
endMaplike();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitElement(long index, Object value, boolean isFirst) {
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
propertyPath.push(Identifier.IT);
|
|
||||||
}
|
|
||||||
var typeName = computeName(collectionType, value);
|
|
||||||
var addedType = false;
|
|
||||||
if (typeName != null) {
|
|
||||||
addedType = true;
|
|
||||||
writePropertyName();
|
|
||||||
startMessage();
|
|
||||||
propertyPath.push(Identifier.get("it_" + typeName));
|
|
||||||
}
|
|
||||||
wrapperRequirement.push(true);
|
|
||||||
visit(value);
|
|
||||||
var popped = wrapperRequirement.pop();
|
|
||||||
assert popped : "Corrupted traversal stack.";
|
|
||||||
if (addedType) {
|
|
||||||
propertyPath.pop();
|
|
||||||
endMessage();
|
|
||||||
}
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
propertyPath.pop();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitEntryKey(Object key, boolean isFirst) {
|
|
||||||
var isDirective = isRenderDirective(key);
|
|
||||||
var isValidKey =
|
|
||||||
isDirective || key instanceof Long || key instanceof Boolean || key instanceof String;
|
|
||||||
if (!isValidKey) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderProtobufMapKey")
|
|
||||||
.withProgramValue("Key", key)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
writePropertyName();
|
|
||||||
startMessage();
|
|
||||||
startNewLine();
|
|
||||||
builder.append("key: ");
|
|
||||||
if (isDirective) {
|
|
||||||
builder.append(VmUtils.readTextProperty(key));
|
|
||||||
} else if (key instanceof String string) {
|
|
||||||
builder.append('"').append(jsonEscaper.escape(string)).append('"');
|
|
||||||
} else {
|
|
||||||
builder.append(key);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitEntryValue(Object value) {
|
|
||||||
propertyPath.push(Identifier.VALUE);
|
|
||||||
visit(value);
|
|
||||||
propertyPath.pop();
|
|
||||||
endMessage();
|
|
||||||
}
|
|
||||||
|
|
||||||
private @Nullable String computeName(@Nullable TypeNode it, Object value) {
|
|
||||||
if (it instanceof UnionTypeNode unionTypeNode) {
|
|
||||||
for (var type : unionTypeNode.getElementTypeNodes()) {
|
|
||||||
if (type instanceof UnionTypeNode) {
|
|
||||||
var computedName = computeName(type, value);
|
|
||||||
if (computedName != null) {
|
|
||||||
return computedName;
|
|
||||||
}
|
|
||||||
} else if (type instanceof NonFinalClassTypeNode) {
|
|
||||||
var clazz = type.getType().getVmClass();
|
|
||||||
if (value instanceof VmValue vmValue) {
|
|
||||||
if (clazz == vmValue.getVmClass()) {
|
|
||||||
return clazz.getSimpleName();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
type.execute(VmUtils.createEmptyMaterializedFrame(), value);
|
|
||||||
} catch (VmTypeMismatchException e) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
return renderType(type);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
protected void visitProperty(Identifier name, Object value, boolean isFirst) {
|
|
||||||
var hasWrapper = false;
|
|
||||||
var hasCollection = false;
|
|
||||||
var prevCollectionType = collectionType;
|
|
||||||
Identifier expectedName = null;
|
|
||||||
propertyPath.push(name);
|
|
||||||
if (enclosingValue instanceof VmTyped) {
|
|
||||||
var clazz = value instanceof VmValue vmValue ? vmValue.getVmClass() : value.getClass();
|
|
||||||
// Compute the name of the field in the wrapper, based on the type, but only if a wrapper
|
|
||||||
// is required.
|
|
||||||
var optionalType =
|
|
||||||
Optional.of(name)
|
|
||||||
.map(enclosingValue.getVmClass()::getProperty)
|
|
||||||
.map(ClassProperty::getTypeNode)
|
|
||||||
.map(PropertyTypeNode::getTypeNode)
|
|
||||||
.map(this::resolveType);
|
|
||||||
if (optionalType.isPresent()) {
|
|
||||||
var type = optionalType.get();
|
|
||||||
var computedName = computeName(type, value);
|
|
||||||
if (computedName != null) {
|
|
||||||
hasWrapper = true;
|
|
||||||
writePropertyName();
|
|
||||||
expectedName = Identifier.get("it_" + computedName);
|
|
||||||
propertyPath.push(expectedName);
|
|
||||||
startMessage();
|
|
||||||
} else if (type instanceof ListingOrMappingTypeNode listingOrMappingType) {
|
|
||||||
hasCollection = true;
|
|
||||||
collectionType = listingOrMappingType.getValueTypeNode();
|
|
||||||
} else if (type instanceof ListTypeNode listType) {
|
|
||||||
hasCollection = true;
|
|
||||||
collectionType = listType.getElementTypeNode();
|
|
||||||
} else if (type instanceof MapTypeNode mapType) {
|
|
||||||
hasCollection = true;
|
|
||||||
collectionType = mapType.getValueTypeNode();
|
|
||||||
} else if (type instanceof SetTypeNode setType) {
|
|
||||||
hasCollection = true;
|
|
||||||
collectionType = setType.getElementTypeNode();
|
|
||||||
} else if (type instanceof NonFinalClassTypeNode) {
|
|
||||||
if (type.getType().getVmClass() != clazz) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderSubtypeForProtobuf", type.getType().getVmClass(), clazz)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
visit(value);
|
|
||||||
if (hasWrapper) {
|
|
||||||
endMessage();
|
|
||||||
var popped = propertyPath.pop();
|
|
||||||
assert popped == expectedName : "Corrupted traversal stack.";
|
|
||||||
} else if (hasCollection) {
|
|
||||||
collectionType = prevCollectionType;
|
|
||||||
}
|
|
||||||
var popped = propertyPath.pop();
|
|
||||||
assert name == popped : "Corrupted traversal stack.";
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startNewLine() {
|
|
||||||
if (indent.isEmpty() || builder.isEmpty() || builder.charAt(builder.length() - 1) == '\n')
|
|
||||||
return;
|
|
||||||
|
|
||||||
builder.append('\n');
|
|
||||||
builder.append(currIndent);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startWrapper() {
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
writePropertyName();
|
|
||||||
startMessage();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void endWrapper() {
|
|
||||||
if (requiresWrapper()) {
|
|
||||||
endMessage();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private boolean requiresWrapper() {
|
|
||||||
var result = wrapperRequirement.peek();
|
|
||||||
assert result != null : "Corrupted traversal stack.";
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void startMessage() {
|
|
||||||
builder.append('{');
|
|
||||||
increaseIndent();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void endMessage() {
|
|
||||||
decreaseIndent();
|
|
||||||
if (builder.charAt(builder.length() - 1) != '{') {
|
|
||||||
startNewLine();
|
|
||||||
}
|
|
||||||
builder.append('}');
|
|
||||||
}
|
|
||||||
|
|
||||||
private void writePropertyName() {
|
|
||||||
if (propertyPath.isEmpty()) return;
|
|
||||||
startNewLine();
|
|
||||||
var name = propertyPath.peek();
|
|
||||||
assert name != null : "Corrupted traversal stack.";
|
|
||||||
builder.append(name);
|
|
||||||
builder.append(": ");
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitString(String value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append('"').append(jsonEscaper.escape(value)).append('"');
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitBoolean(Boolean value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitInt(Long value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitFloat(Double value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitDuration(VmDuration value) {
|
|
||||||
writePropertyName();
|
|
||||||
var nanos = (long) value.convertTo(DurationUnit.NANOS).getValue() % 1000000000;
|
|
||||||
var seconds = (long) Math.floor(value.convertTo(DurationUnit.SECONDS).getValue());
|
|
||||||
startMessage();
|
|
||||||
|
|
||||||
propertyPath.push(SECONDS);
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(seconds);
|
|
||||||
propertyPath.pop();
|
|
||||||
|
|
||||||
propertyPath.push(NANOS);
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(nanos);
|
|
||||||
propertyPath.pop();
|
|
||||||
|
|
||||||
endMessage();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitDataSize(VmDataSize value) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderTypeAddConverter", "DataSize", "Protobuf")
|
|
||||||
.withProgramValue("Value", value)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitBytes(VmBytes value) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderTypeAddConverter", "Bytes", "Protobuf")
|
|
||||||
.withProgramValue("Value", value)
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitIntSeq(VmIntSeq value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value.toPklString());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitPair(VmPair value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value.toPklString());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitRegex(VmRegex value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value.toPklString());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitNull(VmNull value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value.toPklString());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void visitReference(VmReference value) {
|
|
||||||
writePropertyName();
|
|
||||||
builder.append(value.toPklString());
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Resolves types for the purpose of protobuf rendering. "Sees through" nullable types and type
|
|
||||||
* aliases, simplifies variations of {@code Int} and {@code String} types (literate string
|
|
||||||
* types, {@code (U)Int_X_} type aliases, etc.), and checks that map key types are legal for
|
|
||||||
* protobuf.
|
|
||||||
*/
|
|
||||||
// TODO: Memoize?
|
|
||||||
private @Nullable TypeNode resolveType(@Nullable TypeNode type) {
|
|
||||||
if (type instanceof IntTypeNode
|
|
||||||
|| type instanceof StringTypeNode
|
|
||||||
|| type instanceof BooleanTypeNode) {
|
|
||||||
return type;
|
|
||||||
} else if (type instanceof IntSlotTypeNode) {
|
|
||||||
return INT_TYPE;
|
|
||||||
} else if (type instanceof UnionOfStringLiteralsTypeNode
|
|
||||||
|| type instanceof StringLiteralTypeNode) {
|
|
||||||
return STRING_TYPE;
|
|
||||||
} else if (type instanceof NullableTypeNode nullableType) {
|
|
||||||
return resolveType(nullableType.getElementTypeNode());
|
|
||||||
} else if (type instanceof TypeAliasTypeNode typeAliasType) {
|
|
||||||
return resolveType(
|
|
||||||
((VmType.AliasType) typeAliasType.getType()).getVmTypeAlias().getTypeNode());
|
|
||||||
} else if (type instanceof ListingTypeNode listingType) {
|
|
||||||
var valueType = resolveType(listingType.getValueTypeNode());
|
|
||||||
assert valueType != null : "Failed to resolve type node.";
|
|
||||||
|
|
||||||
type =
|
|
||||||
requiresWrapper()
|
|
||||||
? null
|
|
||||||
: new ListingTypeNode(
|
|
||||||
VmUtils.unavailableSourceSection(), VmLanguage.get(null), valueType);
|
|
||||||
return type;
|
|
||||||
} else if (type instanceof MappingTypeNode mappingType) {
|
|
||||||
var keyType = resolveType(mappingType.getKeyTypeNode());
|
|
||||||
if (!(keyType instanceof IntTypeNode
|
|
||||||
|| keyType instanceof StringTypeNode
|
|
||||||
|| keyType instanceof BooleanTypeNode)) {
|
|
||||||
throw new VmExceptionBuilder()
|
|
||||||
.evalError("cannotRenderProtobufMapKeyType")
|
|
||||||
.withSourceSection(type.getSourceSection())
|
|
||||||
.build();
|
|
||||||
}
|
|
||||||
var valueType = resolveType(mappingType.getValueTypeNode());
|
|
||||||
assert valueType != null : "Incomplete or malformed Mapping type";
|
|
||||||
mappingType =
|
|
||||||
new MappingTypeNode(
|
|
||||||
VmUtils.unavailableSourceSection(), VmLanguage.get(null), keyType, valueType);
|
|
||||||
|
|
||||||
type = requiresWrapper() ? null : mappingType;
|
|
||||||
return type;
|
|
||||||
} else if (type instanceof UnionTypeNode) {
|
|
||||||
// Some non-obvious normalization going on here:
|
|
||||||
// - A union type resolves to a union type, unless all element types are string or string
|
|
||||||
// literal types.
|
|
||||||
// - All element types are resolved also.
|
|
||||||
// - All string literal types are combined into a single String case.
|
|
||||||
var hasString = false;
|
|
||||||
var elements = new ArrayList<@Nullable TypeNode>();
|
|
||||||
for (var t : ((UnionTypeNode) type).getElementTypeNodes()) {
|
|
||||||
var resolved = resolveType(t);
|
|
||||||
if (resolved instanceof StringLiteralTypeNode || resolved instanceof StringTypeNode) {
|
|
||||||
if (!hasString) {
|
|
||||||
hasString = true;
|
|
||||||
elements.add(new StringTypeNode(VmUtils.unavailableSourceSection()));
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
elements.add(resolved);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Sort classes with lowest-in-hierarchy first, to correctly derive names for oneOf.
|
|
||||||
elements.sort(
|
|
||||||
(o1, o2) -> {
|
|
||||||
if (o1 instanceof ObjectSlotTypeNode && o2 instanceof ObjectSlotTypeNode) {
|
|
||||||
var t1 = o1.getType().getVmClass();
|
|
||||||
var t2 = o2.getType().getVmClass();
|
|
||||||
if (t1 == null || t2 == null) return 0;
|
|
||||||
return t1.isSubclassOf(t2) ? -1 : t2.isSubclassOf(t1) ? 1 : 0;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
});
|
|
||||||
|
|
||||||
type =
|
|
||||||
hasString && elements.size() == 1
|
|
||||||
? elements.get(0)
|
|
||||||
: new UnionTypeNodeExploded(
|
|
||||||
VmUtils.unavailableSourceSection(), -1, elements.toArray(new TypeNode[0]));
|
|
||||||
return type;
|
|
||||||
}
|
|
||||||
return type;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,4 +0,0 @@
|
|||||||
@NullMarked
|
|
||||||
package org.pkl.core.stdlib.protobuf;
|
|
||||||
|
|
||||||
import org.jspecify.annotations.NullMarked;
|
|
||||||
@@ -619,12 +619,6 @@ Cannot render map with non-scalar key as {0}.
|
|||||||
cannotRenderObjectWithNonScalarKey=\
|
cannotRenderObjectWithNonScalarKey=\
|
||||||
Cannot render object with non-scalar key as {0}.
|
Cannot render object with non-scalar key as {0}.
|
||||||
|
|
||||||
cannotRenderProtobufMapKey=\
|
|
||||||
Cannot render map with a non-scalar, floating point or byte array key.
|
|
||||||
|
|
||||||
cannotRenderProtobufMapKeyType=\
|
|
||||||
Cannot render map with a non-scalar, floating point or byte array key type.
|
|
||||||
|
|
||||||
cannotRenderObjectWithElementsAndOtherMembers=\
|
cannotRenderObjectWithElementsAndOtherMembers=\
|
||||||
Cannot render object with both elements and properties/entries as {0}.
|
Cannot render object with both elements and properties/entries as {0}.
|
||||||
|
|
||||||
@@ -759,17 +753,6 @@ The top-level value of an XML property list must have type `Typed`, `Dynamic`, `
|
|||||||
invalidPropertiesTopLevelValue=\
|
invalidPropertiesTopLevelValue=\
|
||||||
The top-level value of a Java properties file must have type `Typed`, `Dynamic`, `Mapping`, or `Map`, but got type `{0}`.
|
The top-level value of a Java properties file must have type `Typed`, `Dynamic`, `Mapping`, or `Map`, but got type `{0}`.
|
||||||
|
|
||||||
invalidProtobufTopLevelValue=\
|
|
||||||
The top-level value of a protobuf file must have type `Typed`, but got type `{0}`.
|
|
||||||
|
|
||||||
cannotResolveTypeForProtobuf=\
|
|
||||||
Failed to resolve type required for rendering protobuf.\n\
|
|
||||||
\n\
|
|
||||||
Consider adding a type annotation.
|
|
||||||
|
|
||||||
cannotRenderSubtypeForProtobuf=\
|
|
||||||
Cannot render subtype {0} of specified type {1} in protobuf.
|
|
||||||
|
|
||||||
cannotExportValue=\
|
cannotExportValue=\
|
||||||
A value of type `{0}` cannot be exported.
|
A value of type `{0}` cannot be exported.
|
||||||
|
|
||||||
|
|||||||
@@ -1,265 +0,0 @@
|
|||||||
amends "../snippetTest.pkl"
|
|
||||||
|
|
||||||
import "pkl:protobuf"
|
|
||||||
|
|
||||||
local renderer = new protobuf.Renderer {}
|
|
||||||
local function renderValue(it: Any): String =
|
|
||||||
renderer.renderValue(it)
|
|
||||||
|
|
||||||
/// For testing inheritance; [Foo] is the _base_ class.
|
|
||||||
local open class Foo {
|
|
||||||
foo: String
|
|
||||||
}
|
|
||||||
|
|
||||||
/// For testing inheritance; [Bar] is the _derived_ class.
|
|
||||||
local class Bar extends Foo {
|
|
||||||
foo = "Bar"
|
|
||||||
}
|
|
||||||
|
|
||||||
/// For testing the rendering of types inside a `VmTyped`.
|
|
||||||
local class Baz {
|
|
||||||
foo: Foo
|
|
||||||
bar: Bar
|
|
||||||
foos: Listing<Foo>
|
|
||||||
bars: Mapping<String, Bar>
|
|
||||||
}
|
|
||||||
|
|
||||||
/// For testing how rendering deals with _annotated_ (outer) collection types.
|
|
||||||
local class CollectionTypes {
|
|
||||||
emptyList: List<Foo>
|
|
||||||
list: List<Foo> = List(new Bar {}, new Foo { foo = "test foo" })
|
|
||||||
emptyListing: Listing<Foo>
|
|
||||||
listing: Listing<Foo> = new {
|
|
||||||
new Bar { foo = "listing bar" }
|
|
||||||
new Foo { foo = "listing foo" }
|
|
||||||
}
|
|
||||||
emptyMap: Map<Int, String>
|
|
||||||
map: Map<Int, Foo> = Map(
|
|
||||||
1, new Bar { foo = "first" },
|
|
||||||
2, new Foo { foo = "second" }
|
|
||||||
)
|
|
||||||
emptyMapping: Mapping<Int, Bar>
|
|
||||||
mapping: String =
|
|
||||||
module.catch(() ->
|
|
||||||
renderValue(new Mapping<Foo, Bar> {
|
|
||||||
[new Foo { foo = "key foo" }] = new Bar { foo = "value bar" }
|
|
||||||
})
|
|
||||||
)
|
|
||||||
emptySet: Set<Foo>
|
|
||||||
set: Set<Foo> = Set(
|
|
||||||
new Bar { foo = "setOne" },
|
|
||||||
new Bar { foo = "setTwo" }
|
|
||||||
)
|
|
||||||
mappingWithUnannotatedValueType: Mapping<String, Listing> = new {
|
|
||||||
["some"] {
|
|
||||||
new Bar {}
|
|
||||||
new Bar {}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// For testing _admissable_ mapping key types.
|
|
||||||
local class MappingKeys {
|
|
||||||
string: Mapping<String, Bar>
|
|
||||||
long: Mapping<Int, Bar>
|
|
||||||
int: Mapping<Int32, Bar>
|
|
||||||
short: Mapping<Int16, Bar>
|
|
||||||
boolean: Mapping<Boolean, Bar>
|
|
||||||
}
|
|
||||||
|
|
||||||
/// For testing that using _inadmissable_ mapping key types does indeed throw.
|
|
||||||
local class InvalidMappingKey {
|
|
||||||
foo: Mapping<Bar, Bar>
|
|
||||||
}
|
|
||||||
|
|
||||||
local typealias StringLiteralUnion
|
|
||||||
= *"Qux"
|
|
||||||
| "quux"
|
|
||||||
| "QUUX"
|
|
||||||
|
|
||||||
local typealias OpenEndedStringUnion
|
|
||||||
= *"corge"
|
|
||||||
| String // Not a union of string literals, although fully String-y.
|
|
||||||
|
|
||||||
local typealias HeterogeneousUnion
|
|
||||||
= "Grault"
|
|
||||||
| "GRAULT"
|
|
||||||
| Int
|
|
||||||
| Foo
|
|
||||||
|
|
||||||
local typealias SynonymPureEnum = StringLiteralUnion
|
|
||||||
|
|
||||||
local class TypeAliasBehavior {
|
|
||||||
doubleAlias: SynonymPureEnum
|
|
||||||
}
|
|
||||||
|
|
||||||
local class StringLiteralUnionBehavior {
|
|
||||||
theProperty: StringLiteralUnion
|
|
||||||
}
|
|
||||||
|
|
||||||
local class OpenEndedStringUnionBehavior {
|
|
||||||
theProperty: OpenEndedStringUnion
|
|
||||||
}
|
|
||||||
|
|
||||||
local class HeterogeneousUnionBehavior {
|
|
||||||
theHeterogeneousUnion: Listing<HeterogeneousUnion>
|
|
||||||
}
|
|
||||||
|
|
||||||
local class HeterogeneousUnionBehaviorX {
|
|
||||||
theHeterogeneousUnion: HeterogeneousUnion
|
|
||||||
}
|
|
||||||
|
|
||||||
local class InvalidUnionBehavior {
|
|
||||||
myMapping: Mapping<HeterogeneousUnion, Int> = new {
|
|
||||||
[5] = 5
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
local class DynamicBehavior {
|
|
||||||
myDynamic: Dynamic
|
|
||||||
}
|
|
||||||
|
|
||||||
local class DurationBehavior {
|
|
||||||
myDuration: Duration = 42.ns
|
|
||||||
}
|
|
||||||
|
|
||||||
local class DataSizeBehavior {
|
|
||||||
myDataSize: DataSize
|
|
||||||
}
|
|
||||||
|
|
||||||
local class SubtypingBehavior {
|
|
||||||
myFoo: Foo
|
|
||||||
myFooOrBar: (Foo|Bar)?
|
|
||||||
}
|
|
||||||
|
|
||||||
examples {
|
|
||||||
["Rendering primitive values"] {
|
|
||||||
for (v in new Listing {
|
|
||||||
true
|
|
||||||
false
|
|
||||||
|
|
||||||
-42 as Int8
|
|
||||||
-42 as Int16
|
|
||||||
-42 as Int32
|
|
||||||
-42 as Int
|
|
||||||
|
|
||||||
42 as UInt8
|
|
||||||
42 as UInt16
|
|
||||||
42 as UInt32
|
|
||||||
42 as UInt
|
|
||||||
|
|
||||||
-13.37 as Float
|
|
||||||
|
|
||||||
-13.37 as Number
|
|
||||||
13.37 as Number
|
|
||||||
-42 as Number
|
|
||||||
42 as Number
|
|
||||||
|
|
||||||
"Hello world"
|
|
||||||
|
|
||||||
10.min
|
|
||||||
2.ms
|
|
||||||
120.ns
|
|
||||||
5.s + 120.ns
|
|
||||||
}) {
|
|
||||||
renderValue(v)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
["Collection types"] {
|
|
||||||
renderValue(new CollectionTypes {})
|
|
||||||
}
|
|
||||||
|
|
||||||
["Typed objects rendered as protobuf.ProtoMessage"] {
|
|
||||||
renderValue(new Foo { foo = "new" })
|
|
||||||
renderValue(new Bar {})
|
|
||||||
renderValue(new Bar { foo = "Baz" })
|
|
||||||
renderValue(
|
|
||||||
new Baz {
|
|
||||||
foo {
|
|
||||||
foo = "FOO"
|
|
||||||
}
|
|
||||||
foos {
|
|
||||||
foo
|
|
||||||
outer.bar
|
|
||||||
}
|
|
||||||
bars {
|
|
||||||
["default"] {}
|
|
||||||
["amended"] {
|
|
||||||
foo = "Bars"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
)
|
|
||||||
renderValue(new DurationBehavior {})
|
|
||||||
}
|
|
||||||
|
|
||||||
["Unsupported types"] {
|
|
||||||
module.catch(() -> throw(renderValue(new DynamicBehavior {})))
|
|
||||||
module.catch(() -> throw(renderValue(new DataSizeBehavior { myDataSize = 10.kb })))
|
|
||||||
}
|
|
||||||
|
|
||||||
["Types not supported at top-level"] {
|
|
||||||
module.catch(() -> throw(renderValue(Map(3,4))))
|
|
||||||
module.catch(() -> throw(renderValue(new Mapping {[1] = 2})))
|
|
||||||
}
|
|
||||||
|
|
||||||
["Keys in maps"] {
|
|
||||||
renderValue(new MappingKeys {
|
|
||||||
string {
|
|
||||||
["Hello world"] {}
|
|
||||||
}
|
|
||||||
long {
|
|
||||||
[1337] {}
|
|
||||||
}
|
|
||||||
int {
|
|
||||||
[42] {}
|
|
||||||
}
|
|
||||||
short {
|
|
||||||
[1] {}
|
|
||||||
}
|
|
||||||
boolean {
|
|
||||||
[false] {}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
module.catch(() -> throw(renderValue(new InvalidMappingKey {
|
|
||||||
foo {
|
|
||||||
[new Bar {}] {}
|
|
||||||
}
|
|
||||||
})))
|
|
||||||
}
|
|
||||||
|
|
||||||
["typealiases"] {
|
|
||||||
renderValue(new TypeAliasBehavior {})
|
|
||||||
}
|
|
||||||
|
|
||||||
["unions"] {
|
|
||||||
renderValue(new StringLiteralUnionBehavior {})
|
|
||||||
renderValue(new OpenEndedStringUnionBehavior {})
|
|
||||||
renderValue(new HeterogeneousUnionBehaviorX {
|
|
||||||
theHeterogeneousUnion = "Grault"
|
|
||||||
})
|
|
||||||
renderValue(new HeterogeneousUnionBehavior {
|
|
||||||
theHeterogeneousUnion {
|
|
||||||
"Grault"
|
|
||||||
0
|
|
||||||
new Bar {}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
module.catch(() -> renderValue(new InvalidUnionBehavior {}))
|
|
||||||
}
|
|
||||||
["subtypes"] {
|
|
||||||
renderValue(new SubtypingBehavior {
|
|
||||||
myFoo = new Foo { foo = "renders" }
|
|
||||||
})
|
|
||||||
module.catch(() ->
|
|
||||||
renderValue(new SubtypingBehavior {
|
|
||||||
myFoo = new Bar { foo = "shouldn't render" }
|
|
||||||
})
|
|
||||||
)
|
|
||||||
renderValue(new SubtypingBehavior {
|
|
||||||
myFoo = new Foo { foo = "renders" }
|
|
||||||
myFooOrBar = new Bar { foo = "also renders" }
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,75 +0,0 @@
|
|||||||
amends "../snippetTest.pkl"
|
|
||||||
|
|
||||||
import "pkl:protobuf"
|
|
||||||
|
|
||||||
local renderer = new protobuf.Renderer {}
|
|
||||||
|
|
||||||
local class NestedStructures {
|
|
||||||
plainString: String = "plain string"
|
|
||||||
nestedListing: Listing<Listing<String>>
|
|
||||||
nestedListing2: Listing<Listing<Listing<Listing<String>>>>
|
|
||||||
nestedMapping: Mapping<String, Mapping<Int, Boolean>>
|
|
||||||
listingInMapping: Mapping<String, Listing<String>>
|
|
||||||
mappingInListing: Listing<Mapping<Int, Boolean>>
|
|
||||||
nestedList: List<List<String>>
|
|
||||||
nestedMap: Map<String, Map<Int, Boolean>>
|
|
||||||
}
|
|
||||||
|
|
||||||
examples {
|
|
||||||
["some"] {
|
|
||||||
renderer.renderDocument(new NestedStructures {
|
|
||||||
nestedListing {
|
|
||||||
new {
|
|
||||||
"foo"
|
|
||||||
"bar"
|
|
||||||
}
|
|
||||||
new {
|
|
||||||
"baz"
|
|
||||||
"qux"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedListing2 {
|
|
||||||
new {
|
|
||||||
new {
|
|
||||||
new {
|
|
||||||
"foo"
|
|
||||||
"bar"
|
|
||||||
"baz"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedMapping {
|
|
||||||
["quux"] {
|
|
||||||
[42] = true
|
|
||||||
[1337] = false
|
|
||||||
}
|
|
||||||
["corge"] {
|
|
||||||
[0] = false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
listingInMapping {
|
|
||||||
["grault"] {
|
|
||||||
"grault1"
|
|
||||||
"grault2"
|
|
||||||
}
|
|
||||||
["garply"] {
|
|
||||||
"garply1"
|
|
||||||
}
|
|
||||||
["waldo"] {}
|
|
||||||
}
|
|
||||||
mappingInListing {
|
|
||||||
new {
|
|
||||||
[-1] = false
|
|
||||||
[1] = true
|
|
||||||
}
|
|
||||||
new {
|
|
||||||
[-2] = true
|
|
||||||
[2] = false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedList = List(List("pigeon", "plugh"), List(), List("xyzzy"))
|
|
||||||
nestedMap = Map("thud", Map(), "wibble", Map(1, false, 2, true), "wobble", Map(0, false))
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,28 +0,0 @@
|
|||||||
import "pkl:protobuf"
|
|
||||||
|
|
||||||
import ".../input-helper/api/annotationConverter.pkl"
|
|
||||||
|
|
||||||
class Comment extends Annotation
|
|
||||||
|
|
||||||
@protobuf.Property { name = "FOO" }
|
|
||||||
foo: String = "a"
|
|
||||||
|
|
||||||
@annotationConverter.LineComment { text = "bar" }
|
|
||||||
bar: String = "b"
|
|
||||||
|
|
||||||
baz: Nested
|
|
||||||
|
|
||||||
class Nested {
|
|
||||||
@annotationConverter.LineComment { text = "qux" }
|
|
||||||
qux: String = "c"
|
|
||||||
|
|
||||||
quux: String = "c"
|
|
||||||
}
|
|
||||||
|
|
||||||
output {
|
|
||||||
renderer = new protobuf.Renderer {
|
|
||||||
convertPropertyTransformers {
|
|
||||||
[annotationConverter.LineComment] { prefix = " # " }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -2,7 +2,6 @@ amends ".../snippetTest.pkl"
|
|||||||
|
|
||||||
import "pkl:xml"
|
import "pkl:xml"
|
||||||
import "pkl:jsonnet"
|
import "pkl:jsonnet"
|
||||||
import "pkl:protobuf"
|
|
||||||
|
|
||||||
examples {
|
examples {
|
||||||
for (format, renderer in new Mapping {
|
for (format, renderer in new Mapping {
|
||||||
@@ -11,7 +10,6 @@ examples {
|
|||||||
["jsonnet"] = new jsonnet.Renderer {}
|
["jsonnet"] = new jsonnet.Renderer {}
|
||||||
["plist"] = new PListRenderer {}
|
["plist"] = new PListRenderer {}
|
||||||
["properties"] = new PropertiesRenderer {}
|
["properties"] = new PropertiesRenderer {}
|
||||||
["textproto"] = new protobuf.Renderer {}
|
|
||||||
["xml"] = new xml.Renderer {}
|
["xml"] = new xml.Renderer {}
|
||||||
["yaml"] = new YamlRenderer {}
|
["yaml"] = new YamlRenderer {}
|
||||||
}) {
|
}) {
|
||||||
@@ -23,9 +21,6 @@ examples {
|
|||||||
listing = null
|
listing = null
|
||||||
mapping = null
|
mapping = null
|
||||||
}
|
}
|
||||||
when (format == "textproto") {
|
|
||||||
dynamic = null
|
|
||||||
}
|
|
||||||
})
|
})
|
||||||
renderer.renderDocument(new RenderDirective { text = #"✅\❌ /-#;)<>"# })
|
renderer.renderDocument(new RenderDirective { text = #"✅\❌ /-#;)<>"# })
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,13 +2,6 @@ amends ".../snippetTest.pkl"
|
|||||||
|
|
||||||
import "pkl:xml"
|
import "pkl:xml"
|
||||||
import "pkl:jsonnet"
|
import "pkl:jsonnet"
|
||||||
import "pkl:protobuf"
|
|
||||||
|
|
||||||
local class TypedTestCase {
|
|
||||||
property: String
|
|
||||||
elements: Listing<String>
|
|
||||||
entries: Mapping<String, String>
|
|
||||||
}
|
|
||||||
|
|
||||||
examples {
|
examples {
|
||||||
for (format, renderer in new Mapping {
|
for (format, renderer in new Mapping {
|
||||||
@@ -26,16 +19,6 @@ examples {
|
|||||||
[Listing] = (it: Listing) -> it.join(",")
|
[Listing] = (it: Listing) -> it.join(",")
|
||||||
}
|
}
|
||||||
} |> converters
|
} |> converters
|
||||||
["textproto"] = new protobuf.Renderer {
|
|
||||||
converters {
|
|
||||||
[Dynamic] = (it) ->
|
|
||||||
(it) {
|
|
||||||
elements = it.elements.toList().toListing()
|
|
||||||
entries = it.entries.toMap().toMapping()
|
|
||||||
}.toTyped(TypedTestCase)
|
|
||||||
[String] = (it) -> new RenderDirective { text = "(\(it))"}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
["xml"] = new xml.Renderer {} |> converters
|
["xml"] = new xml.Renderer {} |> converters
|
||||||
["yaml"] = new YamlRenderer {} |> converters
|
["yaml"] = new YamlRenderer {} |> converters
|
||||||
}) {
|
}) {
|
||||||
|
|||||||
@@ -1,214 +0,0 @@
|
|||||||
examples {
|
|
||||||
["Rendering primitive values"] {
|
|
||||||
"true"
|
|
||||||
"false"
|
|
||||||
"-42"
|
|
||||||
"-42"
|
|
||||||
"-42"
|
|
||||||
"-42"
|
|
||||||
"42"
|
|
||||||
"42"
|
|
||||||
"42"
|
|
||||||
"42"
|
|
||||||
"-13.37"
|
|
||||||
"-13.37"
|
|
||||||
"13.37"
|
|
||||||
"-42"
|
|
||||||
"42"
|
|
||||||
"\"Hello world\""
|
|
||||||
"""
|
|
||||||
{
|
|
||||||
seconds: 600
|
|
||||||
nanos: 0
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
{
|
|
||||||
seconds: 0
|
|
||||||
nanos: 2000000
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
{
|
|
||||||
seconds: 0
|
|
||||||
nanos: 120
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
{
|
|
||||||
seconds: 5
|
|
||||||
nanos: 120
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
["Collection types"] {
|
|
||||||
"""
|
|
||||||
list: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
list: {
|
|
||||||
foo: "test foo"
|
|
||||||
}
|
|
||||||
listing: {
|
|
||||||
foo: "listing bar"
|
|
||||||
}
|
|
||||||
listing: {
|
|
||||||
foo: "listing foo"
|
|
||||||
}
|
|
||||||
map: {
|
|
||||||
key: 1
|
|
||||||
value: {
|
|
||||||
foo: "first"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
map: {
|
|
||||||
key: 2
|
|
||||||
value: {
|
|
||||||
foo: "second"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mapping: "Cannot call method `renderValue` from here because it is not `const`."
|
|
||||||
set: {
|
|
||||||
foo: "setOne"
|
|
||||||
}
|
|
||||||
set: {
|
|
||||||
foo: "setTwo"
|
|
||||||
}
|
|
||||||
mappingWithUnannotatedValueType: {
|
|
||||||
key: "some"
|
|
||||||
value: {
|
|
||||||
it: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
it: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
["Typed objects rendered as protobuf.ProtoMessage"] {
|
|
||||||
"foo: \"new\""
|
|
||||||
"foo: \"Bar\""
|
|
||||||
"foo: \"Baz\""
|
|
||||||
"""
|
|
||||||
foo: {
|
|
||||||
foo: "FOO"
|
|
||||||
}
|
|
||||||
bar: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
foos: {
|
|
||||||
foo: "FOO"
|
|
||||||
}
|
|
||||||
foos: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
bars: {
|
|
||||||
key: "default"
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
bars: {
|
|
||||||
key: "amended"
|
|
||||||
value: {
|
|
||||||
foo: "Bars"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
myDuration: {
|
|
||||||
seconds: 0
|
|
||||||
nanos: 42
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
["Unsupported types"] {
|
|
||||||
"Cannot render value of type `Dynamic` as Protobuf. Value: new Dynamic {}"
|
|
||||||
"Cannot render value of type `DataSize` as Protobuf. Value: 10.kb"
|
|
||||||
}
|
|
||||||
["Types not supported at top-level"] {
|
|
||||||
"The top-level value of a protobuf file must have type `Typed`, but got type `Map`."
|
|
||||||
"The top-level value of a protobuf file must have type `Typed`, but got type `Mapping`."
|
|
||||||
}
|
|
||||||
["Keys in maps"] {
|
|
||||||
"""
|
|
||||||
string: {
|
|
||||||
key: "Hello world"
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
long: {
|
|
||||||
key: 1337
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
int: {
|
|
||||||
key: 42
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
short: {
|
|
||||||
key: 1
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
boolean: {
|
|
||||||
key: false
|
|
||||||
value: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"Cannot render map with a non-scalar, floating point or byte array key type."
|
|
||||||
}
|
|
||||||
["typealiases"] {
|
|
||||||
"doubleAlias: \"Qux\""
|
|
||||||
}
|
|
||||||
["unions"] {
|
|
||||||
"theProperty: \"Qux\""
|
|
||||||
"theProperty: \"corge\""
|
|
||||||
"""
|
|
||||||
theHeterogeneousUnion: {
|
|
||||||
it_String: "Grault"
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
theHeterogeneousUnion: {
|
|
||||||
it_String: "Grault"
|
|
||||||
}
|
|
||||||
theHeterogeneousUnion: {
|
|
||||||
it_Int: 0
|
|
||||||
}
|
|
||||||
theHeterogeneousUnion: {
|
|
||||||
it_Foo: {
|
|
||||||
foo: "Bar"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"Cannot render map with a non-scalar, floating point or byte array key type."
|
|
||||||
}
|
|
||||||
["subtypes"] {
|
|
||||||
"""
|
|
||||||
myFoo: {
|
|
||||||
foo: "renders"
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
"Cannot render subtype protobuf#Foo of specified type protobuf#Bar in protobuf."
|
|
||||||
"""
|
|
||||||
myFoo: {
|
|
||||||
foo: "renders"
|
|
||||||
}
|
|
||||||
myFooOrBar: {
|
|
||||||
it_Bar: {
|
|
||||||
foo: "also renders"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,118 +0,0 @@
|
|||||||
examples {
|
|
||||||
["some"] {
|
|
||||||
"""
|
|
||||||
plainString: "plain string"
|
|
||||||
nestedListing: {
|
|
||||||
it: "foo"
|
|
||||||
it: "bar"
|
|
||||||
}
|
|
||||||
nestedListing: {
|
|
||||||
it: "baz"
|
|
||||||
it: "qux"
|
|
||||||
}
|
|
||||||
nestedListing2: {
|
|
||||||
it: {
|
|
||||||
it: {
|
|
||||||
it: "foo"
|
|
||||||
it: "bar"
|
|
||||||
it: "baz"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedMapping: {
|
|
||||||
key: "quux"
|
|
||||||
value: {
|
|
||||||
it: {
|
|
||||||
key: 42
|
|
||||||
value: true
|
|
||||||
}
|
|
||||||
it: {
|
|
||||||
key: 1337
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedMapping: {
|
|
||||||
key: "corge"
|
|
||||||
value: {
|
|
||||||
it: {
|
|
||||||
key: 0
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
listingInMapping: {
|
|
||||||
key: "grault"
|
|
||||||
value: {
|
|
||||||
it: "grault1"
|
|
||||||
it: "grault2"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
listingInMapping: {
|
|
||||||
key: "garply"
|
|
||||||
value: {
|
|
||||||
it: "garply1"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
listingInMapping: {
|
|
||||||
key: "waldo"
|
|
||||||
value: {}
|
|
||||||
}
|
|
||||||
mappingInListing: {
|
|
||||||
it: {
|
|
||||||
key: -1
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
it: {
|
|
||||||
key: 1
|
|
||||||
value: true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mappingInListing: {
|
|
||||||
it: {
|
|
||||||
key: -2
|
|
||||||
value: true
|
|
||||||
}
|
|
||||||
it: {
|
|
||||||
key: 2
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedList: {
|
|
||||||
it: "pigeon"
|
|
||||||
it: "plugh"
|
|
||||||
}
|
|
||||||
nestedList: {}
|
|
||||||
nestedList: {
|
|
||||||
it: "xyzzy"
|
|
||||||
}
|
|
||||||
nestedMap: {
|
|
||||||
key: "thud"
|
|
||||||
value: {}
|
|
||||||
}
|
|
||||||
nestedMap: {
|
|
||||||
key: "wibble"
|
|
||||||
value: {
|
|
||||||
it: {
|
|
||||||
key: 1
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
it: {
|
|
||||||
key: 2
|
|
||||||
value: true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
nestedMap: {
|
|
||||||
key: "wobble"
|
|
||||||
value: {
|
|
||||||
it: {
|
|
||||||
key: 0
|
|
||||||
value: false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,6 +0,0 @@
|
|||||||
FOO: "a"
|
|
||||||
bar: "b" # bar
|
|
||||||
baz: {
|
|
||||||
qux: "c" # qux
|
|
||||||
quux: "c"
|
|
||||||
}
|
|
||||||
@@ -176,37 +176,6 @@ examples {
|
|||||||
"""
|
"""
|
||||||
"✅\\❌ /-#;)<>"
|
"✅\\❌ /-#;)<>"
|
||||||
}
|
}
|
||||||
["textproto"] {
|
|
||||||
"""
|
|
||||||
1"2
|
|
||||||
3\t4'
|
|
||||||
"""
|
|
||||||
"+* /\\-;)❌#✅<>"
|
|
||||||
"""
|
|
||||||
directiveProperty: ✅/&\\;)*❌
|
|
||||||
normalProperty: 42
|
|
||||||
listing: "foo"
|
|
||||||
listing: 💰
|
|
||||||
listing: "baz"
|
|
||||||
mapping: {
|
|
||||||
key: "key"
|
|
||||||
value: "value"
|
|
||||||
}
|
|
||||||
mapping: {
|
|
||||||
key: 🔑
|
|
||||||
value: 42
|
|
||||||
}
|
|
||||||
mapping: {
|
|
||||||
key: "other"
|
|
||||||
value: 💰
|
|
||||||
}
|
|
||||||
|
|
||||||
"""
|
|
||||||
"""
|
|
||||||
✅\\❌ /-#;)<>
|
|
||||||
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
["xml"] {
|
["xml"] {
|
||||||
"""
|
"""
|
||||||
1"2
|
1"2
|
||||||
|
|||||||
@@ -79,22 +79,6 @@ examples {
|
|||||||
|
|
||||||
"""
|
"""
|
||||||
}
|
}
|
||||||
["textproto"] {
|
|
||||||
"""
|
|
||||||
property: (value)
|
|
||||||
elements: (element1)
|
|
||||||
elements: (element2)
|
|
||||||
entries: {
|
|
||||||
key: (key1)
|
|
||||||
value: (value1)
|
|
||||||
}
|
|
||||||
entries: {
|
|
||||||
key: (key2)
|
|
||||||
value: (value2)
|
|
||||||
}
|
|
||||||
|
|
||||||
"""
|
|
||||||
}
|
|
||||||
["xml"] {
|
["xml"] {
|
||||||
"""
|
"""
|
||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
|||||||
-1
@@ -20,7 +20,6 @@ pkl:net
|
|||||||
pkl:pklbinary
|
pkl:pklbinary
|
||||||
pkl:platform
|
pkl:platform
|
||||||
pkl:Project
|
pkl:Project
|
||||||
pkl:protobuf
|
|
||||||
pkl:ref
|
pkl:ref
|
||||||
pkl:reflect
|
pkl:reflect
|
||||||
pkl:release
|
pkl:release
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright © 2024-2025 Apple Inc. and the Pkl project authors. All rights reserved.
|
* Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -30,7 +30,6 @@ class ReflectModuleTest {
|
|||||||
"pkl:json",
|
"pkl:json",
|
||||||
"pkl:jsonnet",
|
"pkl:jsonnet",
|
||||||
"pkl:math",
|
"pkl:math",
|
||||||
"pkl:protobuf",
|
|
||||||
"pkl:reflect",
|
"pkl:reflect",
|
||||||
"pkl:settings",
|
"pkl:settings",
|
||||||
"pkl:shell",
|
"pkl:shell",
|
||||||
|
|||||||
@@ -1,26 +0,0 @@
|
|||||||
start_timestamp_ms: 0
|
|
||||||
end_timestamp_ms: 100
|
|
||||||
people: {
|
|
||||||
key: "Pigeon"
|
|
||||||
value: {
|
|
||||||
name: "Pigeon"
|
|
||||||
profile: {
|
|
||||||
isExtinct: false
|
|
||||||
}
|
|
||||||
fictional: true
|
|
||||||
height: 1.77
|
|
||||||
hobbies: "cooing"
|
|
||||||
role: Lead
|
|
||||||
}
|
|
||||||
}
|
|
||||||
people: {
|
|
||||||
key: "Parrot"
|
|
||||||
value: {
|
|
||||||
name: "Parrot"
|
|
||||||
fictional: true
|
|
||||||
height: 1.76
|
|
||||||
hobbies: "singing"
|
|
||||||
role: Lead
|
|
||||||
}
|
|
||||||
}
|
|
||||||
owner: "Pigeon"
|
|
||||||
+1
-4
@@ -26,7 +26,6 @@ import "pkl:math"
|
|||||||
import "pkl:net"
|
import "pkl:net"
|
||||||
import "pkl:pklbinary"
|
import "pkl:pklbinary"
|
||||||
// noinspection Deprecated
|
// noinspection Deprecated
|
||||||
import "pkl:protobuf"
|
|
||||||
import "pkl:xml"
|
import "pkl:xml"
|
||||||
import "pkl:yaml"
|
import "pkl:yaml"
|
||||||
|
|
||||||
@@ -116,8 +115,6 @@ abstract external class Module {
|
|||||||
new PListRenderer {}
|
new PListRenderer {}
|
||||||
else if (format == "properties")
|
else if (format == "properties")
|
||||||
new PropertiesRenderer {}
|
new PropertiesRenderer {}
|
||||||
else if (format == "textproto")
|
|
||||||
new protobuf.Renderer {}
|
|
||||||
else if (format == "xml")
|
else if (format == "xml")
|
||||||
new xml.Renderer {}
|
new xml.Renderer {}
|
||||||
else if (format == "yaml")
|
else if (format == "yaml")
|
||||||
@@ -126,7 +123,7 @@ abstract external class Module {
|
|||||||
new pklbinary.Renderer {}
|
new pklbinary.Renderer {}
|
||||||
else
|
else
|
||||||
throw(
|
throw(
|
||||||
"Unknown output format: `\(format)`. Supported formats are `json`, `jsonnet`, `pcf`, `plist`, `properties`, `textproto`, `xml`, `yaml`, `pkl-binary`."
|
"Unknown output format: `\(format)`. Supported formats are `json`, `jsonnet`, `pcf`, `plist`, `properties`, `xml`, `yaml`, `pkl-binary`."
|
||||||
)
|
)
|
||||||
text =
|
text =
|
||||||
if (renderer is ValueRenderer)
|
if (renderer is ValueRenderer)
|
||||||
|
|||||||
@@ -1,66 +0,0 @@
|
|||||||
//===----------------------------------------------------------------------===//
|
|
||||||
// Copyright © 2024-2026 Apple Inc. and the Pkl project authors. All rights reserved.
|
|
||||||
//
|
|
||||||
// Licensed 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
|
|
||||||
//
|
|
||||||
// https://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.
|
|
||||||
//===----------------------------------------------------------------------===//
|
|
||||||
|
|
||||||
/// A renderer for [Protocol Buffers](https://developers.google.com/protocol-buffers).
|
|
||||||
///
|
|
||||||
/// WARNING:
|
|
||||||
/// This module is deprecated, and scheduled for removal without replacement.
|
|
||||||
/// For rendering into a protobuf wire format, consider rendering to
|
|
||||||
/// [ProtoJSON](https://protobuf.dev/programming-guides/json/) using [json.Renderer].
|
|
||||||
@ModuleInfo { minPklVersion = "0.34.0" }
|
|
||||||
@Deprecated { since = "0.33.0"; message = "Scheduled for removal without replacement" }
|
|
||||||
module pkl.protobuf
|
|
||||||
|
|
||||||
import "pkl:json"
|
|
||||||
import "pkl:reflect"
|
|
||||||
|
|
||||||
/// A renderer for [Protocol Buffers](https://developers.google.com/protocol-buffers).
|
|
||||||
/// Note: This class is _experimental_ and not ready for production use.
|
|
||||||
///
|
|
||||||
/// As of this release, only Protocol Buffers' text format is supported.
|
|
||||||
///
|
|
||||||
/// The [Property] annotation can be used to change how a property name renders into Protobuf.
|
|
||||||
///
|
|
||||||
/// Example:
|
|
||||||
/// ```
|
|
||||||
/// import "pkl:protobuf"
|
|
||||||
///
|
|
||||||
/// @protobuf.Property { name = "wing_span" }
|
|
||||||
/// wingSpan: Int
|
|
||||||
/// ```
|
|
||||||
class Renderer extends ValueRenderer {
|
|
||||||
/// The characters to use for indenting output.
|
|
||||||
///
|
|
||||||
/// Defaults to two spaces.
|
|
||||||
indent: String = " "
|
|
||||||
|
|
||||||
external function renderDocument(value: Any): String
|
|
||||||
|
|
||||||
external function renderValue(value: Any): String
|
|
||||||
|
|
||||||
/// Returns the canonical name for [type].
|
|
||||||
external function renderType(type: reflect.Type): String
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Annotate properties of classes and modules with this class to override how a [Renderer]
|
|
||||||
/// interprets a property's name.
|
|
||||||
@Since { version = "0.31.0" }
|
|
||||||
class Property extends ConvertProperty {
|
|
||||||
/// The new name to use for the annotated property when rendered by [Renderer].
|
|
||||||
name: String
|
|
||||||
|
|
||||||
render = (prop, renderer) -> if (renderer is Renderer) Pair(name, prop.value) else prop
|
|
||||||
}
|
|
||||||
Reference in new issue
Block a user