Skip to content
This repository was archived by the owner on Jun 20, 2024. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,7 @@ These apply to specifically marked enums, giving you more finely-grained control

- [enums_as_constants](internal/converter/testdata/proto/ImportedEnum.proto): Encode ENUMs (and their annotations) as CONST
- [enums_as_strings_only](internal/converter/testdata/proto/OptionEnumsAsStringsOnly.proto): ENUM values are only strings (not the numeric counterparts)
- [enums_trim_prefix](internal/converter/testdata/proto/OptionEnumsTrimPrefix.proto): ENUM values have enum name prefix removed

### Field Options

Expand Down
26 changes: 23 additions & 3 deletions internal/converter/converter.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,15 @@ import (
"strings"

"github.com/alecthomas/jsonschema"
"github.com/chrusty/protoc-gen-jsonschema/internal/protos"
"github.com/iancoleman/strcase"
"github.com/sirupsen/logrus"
"github.com/xeipuuv/gojsonschema"
gengo "google.golang.org/protobuf/cmd/protoc-gen-go/internal_gengo"
"google.golang.org/protobuf/proto"
descriptor "google.golang.org/protobuf/types/descriptorpb"
plugin "google.golang.org/protobuf/types/pluginpb"

"github.com/chrusty/protoc-gen-jsonschema/internal/protos"
)

const (
Expand Down Expand Up @@ -52,6 +54,7 @@ type ConverterFlags struct {
EnforceOneOf bool
EnumsAsConstants bool
EnumsAsStringsOnly bool
EnumsTrimPrefix bool
KeepNewLinesInDescription bool
PrefixSchemaFilesWithPackage bool
UseJSONFieldnamesOnly bool
Expand Down Expand Up @@ -106,6 +109,8 @@ func (c *Converter) parseGeneratorParameters(parameters string) {
c.Flags.EnforceOneOf = true
case "enums_as_strings_only":
c.Flags.EnumsAsStringsOnly = true
case "enums_trim_prefix":
c.Flags.EnumsTrimPrefix = true
case "json_fieldnames":
c.Flags.UseJSONFieldnamesOnly = true
case "prefix_schema_files_with_package":
Expand Down Expand Up @@ -151,6 +156,11 @@ func (c *Converter) convertEnumType(enum *descriptor.EnumDescriptorProto, conver
if enumOptions.GetEnumsAsStringsOnly() {
converterFlags.EnumsAsStringsOnly = true
}

// ENUM values trim enum name prefix:
if enumOptions.GetEnumsTrimPrefix() {
converterFlags.EnumsTrimPrefix = true
}
}
}
}
Expand Down Expand Up @@ -182,6 +192,9 @@ func (c *Converter) convertEnumType(enum *descriptor.EnumDescriptorProto, conver
jsonSchemaType.OneOf = nil
}

// If we need to trim prefix from enum value
enumNamePrefix := fmt.Sprintf("%s_", strcase.ToScreamingSnake(*enum.Name))

// We have found an enum, append its values:
for _, value := range enum.Value {

Expand All @@ -191,17 +204,24 @@ func (c *Converter) convertEnumType(enum *descriptor.EnumDescriptorProto, conver
_, valueDescription = c.formatTitleAndDescription(nil, src)
}

valueName := value.GetName()

// If enum name prefix should be removed from enum value name:
if converterFlags.EnumsTrimPrefix {
valueName = strings.TrimPrefix(valueName, enumNamePrefix)
}

// If we're using constants for ENUMs then add these here, along with their title:
if converterFlags.EnumsAsConstants {
c.schemaVersion = versionDraft06 // Const requires draft-06
jsonSchemaType.OneOf = append(jsonSchemaType.OneOf, &jsonschema.Type{Extras: map[string]interface{}{"const": value.GetName()}, Description: valueDescription})
jsonSchemaType.OneOf = append(jsonSchemaType.OneOf, &jsonschema.Type{Extras: map[string]interface{}{"const": valueName}, Description: valueDescription})
if !converterFlags.EnumsAsStringsOnly {
jsonSchemaType.OneOf = append(jsonSchemaType.OneOf, &jsonschema.Type{Extras: map[string]interface{}{"const": value.GetNumber()}, Description: valueDescription})
}
}

// Add the values to the ENUM:
jsonSchemaType.Enum = append(jsonSchemaType.Enum, value.Name)
jsonSchemaType.Enum = append(jsonSchemaType.Enum, valueName)
if !converterFlags.EnumsAsStringsOnly {
jsonSchemaType.Enum = append(jsonSchemaType.Enum, value.Number)
}
Expand Down
10 changes: 10 additions & 0 deletions internal/converter/converter_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -307,6 +307,16 @@ func configureSampleProtos() map[string]sampleProto {
ObjectsToValidateFail: []string{testdata.OptionEnumsAsStringsOnlyFail},
ObjectsToValidatePass: []string{testdata.OptionEnumsAsStringsOnlyPass},
},
"OptionEnumsTrimPrefix": {
Flags: ConverterFlags{
EnumsTrimPrefix: true,
},
ExpectedJSONSchema: []string{testdata.OptionEnumsTrimPrefix},
FilesToGenerate: []string{"OptionEnumsTrimPrefix.proto"},
ProtoFileName: "OptionEnumsTrimPrefix.proto",
ObjectsToValidateFail: []string{testdata.OptionEnumsTrimPrefixFail},
ObjectsToValidatePass: []string{testdata.OptionEnumsTrimPrefixPass},
},
"OptionFileExtension": {
ExpectedJSONSchema: []string{testdata.OptionFileExtension},
ExpectedFileNames: []string{"OptionFileExtension.jsonschema"},
Expand Down
16 changes: 16 additions & 0 deletions internal/converter/testdata/option_enums_trim_prefix.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package testdata

const OptionEnumsTrimPrefix = `{
"$schema": "http://json-schema.org/draft-04/schema#",
"enum": [
"UNSPECIFIED",
"HTTP",
"HTTPS"
],
"type": "string",
"title": "Scheme"
}`

const OptionEnumsTrimPrefixPass = `"HTTP"`

const OptionEnumsTrimPrefixFail = `4`
14 changes: 14 additions & 0 deletions internal/converter/testdata/proto/OptionEnumsTrimPrefix.proto
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
syntax = "proto3";
package samples;
import "options.proto";

enum Scheme {
option (protoc.gen.jsonschema.enum_options).enums_trim_prefix = true;

// for test
option (protoc.gen.jsonschema.enum_options).enums_as_strings_only = true;

SCHEME_UNSPECIFIED = 0;
SCHEME_HTTP = 1;
SCHEME_HTTPS = 2;
}
3 changes: 2 additions & 1 deletion internal/converter/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,12 @@ import (
"strings"

"github.com/alecthomas/jsonschema"
"github.com/chrusty/protoc-gen-jsonschema/internal/protos"
"github.com/iancoleman/orderedmap"
"github.com/xeipuuv/gojsonschema"
"google.golang.org/protobuf/proto"
descriptor "google.golang.org/protobuf/types/descriptorpb"

"github.com/chrusty/protoc-gen-jsonschema/internal/protos"
)

var (
Expand Down
89 changes: 50 additions & 39 deletions internal/protos/options.pb.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions jsonschemas/EnumOptions.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,10 @@
"enums_as_strings_only": {
"type": "boolean",
"description": "Enums tagged with this will only provide string values as options (not their numerical equivalents):"
},
"enums_trim_prefix": {
"type": "boolean",
"description": "Enums tagged with this will have enum name prefix removed from values:"
}
},
"additionalProperties": true,
Expand Down
3 changes: 3 additions & 0 deletions options.proto
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,9 @@ message EnumOptions {

// Enums tagged with this will only provide string values as options (not their numerical equivalents):
bool enums_as_strings_only = 2;

// Enums tagged with this will have enum name prefix removed from values:
bool enums_trim_prefix = 3;
}


Expand Down