ahamez / protox

A fast, easy to use and 100% conformant Elixir library for Google Protocol Buffers (aka protobuf)

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

protox and the `package` directive (was: Proposal - Support Namespace definition when use files generation)

xinz opened this issue · comments

commented

Hello,

First of all, thank you.

When use *.proto files to generate modules, currently, it does not support namespace definition by each *.proto file, do we have any plan about this feature?

Thanks.

Hello,

Indeed, it's currently not possible to have a different namespace per file. While it's not impossible to write some code for to support this, it will be quite cumbersome to develop as the library would have to track the origin file for each entity defined.

Furthermore, I think it can collide with the package mechanism of protobuf. For instance, if you have several *.proto files that define the same package, then having a namespace per file would break the resolution of types as they would be prefixed by a different namespace.

But maybe you have a specific use-case in mind that protobuf's package does not cover?

commented

Hi,

In my use case, each *.proto file defines as a set of functions, so when generate the Elixir modules hope to add the corresponding functional Namespace as a prefix.

Let's take an example foo.proto as below:

syntax = "proto2";

package foo;

message MatchQuery {
    optional string field_name = 1;
    optional string text = 2;
}

message MatchPhraseQuery {
    optional string field_name = 1;
    optional string text = 2;
}

For example use exprotobuf to define a module by the foo.proto file.

defmodule Foo do
  @moduledoc false
  use Protobuf, from: Path.expand("./foo.proto", __DIR__)
end

For example use protobuf-elixir to add module namespace in the generation module files, it supports to define module prefix in the foo.proto file, see details

syntax = "proto2";
package foo;
import "elixirpb.proto";
option (elixirpb.file).module_prefix = "Foo";

The above examples both can use Foo.MatchQuery and Foo.MatchPhraseQuery modules.

Refer the official document of protobuf, the package directive is optional, which is supported by the library/language. The protobuf's package may cover my use case in my opinion, if protox plans to support add module prefix by use package, this use case need to modify each package name of *.proto file, but so far my use case the package naming is not in strict restrictions.

In the *.proto files generation, personally, I prefer the similar use of protobuf-elixir, but use package directive looks like may be simple once clarified, WDYT?

Hope I explain my use case clear, thanks for your reply.

protox uses the package directive. So, let's say we have the following content in a .proto file:

syntax = "proto3";

  package fiz;

  message Baz {
  }

  message Foo {
    int32 a = 1;
    map<int32, Baz> b = 2;
  }

Then, protox will generate Fiz.Baz and Fiz.Foo. It this what you need?

Nevertheless, I will add a clarification in the documentation to make sure it's clear that protox does use the package directive.

commented

Thanks for your clarification, after define the package directive in the elixir module naming format, e.g. Foo.Bar, it works fine for me to use protox, appreciates to the document updates.