Beispiel #1
0
  def test_check_duplicate_conflicting_protos_error(self):
    file1 = self.create_file('src1/foo.proto', dedent('''
        package com.example.test_proto;
        message Foo{value=1;}
      '''))

    # Create an  .proto file in a different directory that has a different definition
    file2 = self.create_file('src2/foo.proto', dedent('''
        package com.example.test_proto;
        message Foo{}
      '''))

    task = self.create_task(self.context())
    test_logger = self.MockLogger()
    sources_by_base = OrderedDict()
    sources_by_base[os.path.join(self.build_root, 'src1')] = [file1]
    sources_by_base[os.path.join(self.build_root, 'src2')] = [file2]

    check_duplicate_conflicting_protos(task, sources_by_base, [file1, file2], test_logger)

    self.assertEquals(1, len(test_logger._warn))

    self.assertRegexpMatches(test_logger._warn[0], 'Arbitrarily favoring proto 1')
    self.assertEquals(1, len(test_logger._error))
    self.assertRegexpMatches(test_logger._error[0], '^Proto conflict detected.*\n.*src1/foo.proto\n.*src2/foo.proto')
Beispiel #2
0
  def test_check_duplicate_conflicting_protos_warn(self):
    file1 = self.create_file('src1/foo.proto', dedent('''
      package com.example.test_proto;
      message Foo{}
    '''))

    # Create an identical .proto file in a different directory
    file2 = self.create_file('src2/foo.proto', dedent('''
      package com.example.test_proto;
      message Foo{}
    '''))

    task = self.create_task(self.context())
    test_logger = self.MockLogger()
    sources_by_base = OrderedDict()
    sources_by_base[os.path.join(self.build_root, 'src1')] = [file1]
    sources_by_base[os.path.join(self.build_root, 'src2')] = [file2]

    check_duplicate_conflicting_protos(task, sources_by_base, [file1, file2], test_logger)

    self.assertEquals(2, len(test_logger._warn), '\n'.join([re.sub('\\n', '\\\\n', s) for s in test_logger._warn]))
    self.assertRegexpMatches(test_logger._warn[0], '^Proto duplication detected.*\n.*src1/foo.proto\n.*src2/foo.proto')
    self.assertRegexpMatches(test_logger._warn[1], 'Arbitrarily favoring proto 1')

    self.assertEquals([], test_logger._error)
Beispiel #3
0
    def execute_codegen(self, targets):
        # Invoke the generator once per target.  Because the wire compiler has flags that try to reduce
        # the amount of code emitted, Invoking them all together will break if one target specifies a
        # service_writer and another does not, or if one specifies roots and another does not.
        for target in targets:
            sources_by_base = self._calculate_sources([target])
            if self.codegen_strategy.name() == 'isolated':
                sources = OrderedSet(target.sources_relative_to_buildroot())
            else:
                sources = OrderedSet(
                    itertools.chain.from_iterable(sources_by_base.values()))
            if not self.validate_sources_present(sources, [target]):
                continue
            relative_sources = OrderedSet()
            for source in sources:
                source_root = SourceRoot.find_by_path(source)
                if not source_root:
                    source_root = SourceRoot.find(target)
                relative_source = os.path.relpath(source, source_root)
                relative_sources.add(relative_source)
            check_duplicate_conflicting_protos(self, sources_by_base,
                                               relative_sources,
                                               self.context.log)

            args = ['--java_out={0}'.format(self.codegen_workdir(target))]

            # Add all params in payload to args

            if target.payload.get_field_value('no_options'):
                args.append('--no_options')

            service_writer = target.payload.service_writer
            if service_writer:
                args.append('--service_writer={0}'.format(service_writer))

            registry_class = target.payload.registry_class
            if registry_class:
                args.append('--registry_class={0}'.format(registry_class))

            if target.payload.roots:
                args.append('--roots={0}'.format(','.join(
                    target.payload.roots)))

            if target.payload.enum_options:
                args.append('--enum_options={0}'.format(','.join(
                    target.payload.enum_options)))

            args.append('--proto_path={0}'.format(
                os.path.join(get_buildroot(), SourceRoot.find(target))))

            args.extend(relative_sources)

            result = util.execute_java(
                classpath=self.tool_classpath('wire-compiler'),
                main='com.squareup.wire.WireCompiler',
                args=args)
            if result != 0:
                raise TaskError(
                    'Wire compiler exited non-zero ({0})'.format(result))
Beispiel #4
0
  def execute_codegen(self, targets):
    # Invoke the generator once per target.  Because the wire compiler has flags that try to reduce
    # the amount of code emitted, Invoking them all together will break if one target specifies a
    # service_writer and another does not, or if one specifies roots and another does not.
    for target in targets:
      sources_by_base = self._calculate_sources([target])
      if self.codegen_strategy.name() == 'isolated':
        sources = OrderedSet(target.sources_relative_to_buildroot())
      else:
        sources = OrderedSet(itertools.chain.from_iterable(sources_by_base.values()))
      if not self.validate_sources_present(sources, [target]):
        continue
      relative_sources = OrderedSet()
      for source in sources:
        source_root = SourceRoot.find_by_path(source)
        if not source_root:
          source_root = SourceRoot.find(target)
        relative_source = os.path.relpath(source, source_root)
        relative_sources.add(relative_source)
      check_duplicate_conflicting_protos(self, sources_by_base, relative_sources, self.context.log)

      args = ['--java_out={0}'.format(self.codegen_workdir(target))]

      # Add all params in payload to args

      if target.payload.get_field_value('no_options'):
        args.append('--no_options')

      service_writer = target.payload.service_writer
      if service_writer:
        args.append('--service_writer={0}'.format(service_writer))

      registry_class = target.payload.registry_class
      if registry_class:
        args.append('--registry_class={0}'.format(registry_class))

      if target.payload.roots:
        args.append('--roots={0}'.format(','.join(target.payload.roots)))

      if target.payload.enum_options:
        args.append('--enum_options={0}'.format(','.join(target.payload.enum_options)))

      args.append('--proto_path={0}'.format(os.path.join(get_buildroot(),
                                                         SourceRoot.find(target))))

      args.extend(relative_sources)

      result = util.execute_java(classpath=self.tool_classpath('wire-compiler'),
                                 main='com.squareup.wire.WireCompiler',
                                 args=args)
      if result != 0:
        raise TaskError('Wire compiler exited non-zero ({0})'.format(result))
Beispiel #5
0
    def genlang(self, lang, targets):
        # Invoke the generator once per target.  Because the wire compiler has flags that try to reduce
        # the amount of code emitted, Invoking them all together will break if one target specifies a
        # service_writer and another does not, or if one specifies roots and another does not.
        for target in targets:
            sources_by_base = self._calculate_sources([target])
            sources = OrderedSet(itertools.chain.from_iterable(sources_by_base.values()))
            relative_sources = OrderedSet()
            for source in sources:
                source_root = SourceRoot.find_by_path(source)
                if not source_root:
                    source_root = SourceRoot.find(target)
                relative_source = os.path.relpath(source, source_root)
                relative_sources.add(relative_source)
            check_duplicate_conflicting_protos(self, sources_by_base, relative_sources, self.context.log)

            if lang != "java":
                raise TaskError("Unrecognized wire gen lang: {0}".format(lang))

            args = ["--java_out={0}".format(self.java_out)]

            # Add all params in payload to args

            if target.payload.get_field_value("no_options"):
                args.append("--no_options")

            service_writer = target.payload.service_writer
            if service_writer:
                args.append("--service_writer={0}".format(service_writer))

            registry_class = target.payload.registry_class
            if registry_class:
                args.append("--registry_class={0}".format(registry_class))

            for root in target.payload.roots:
                args.append("--roots={0}".format(root))

            for enum_option in target.payload.enum_options:
                args.append("--enum_options={0}".format(enum_option))

            args.append("--proto_path={0}".format(os.path.join(get_buildroot(), SourceRoot.find(target))))

            args.extend(relative_sources)

            result = util.execute_java(
                classpath=self.tool_classpath("wire-compiler"), main="com.squareup.wire.WireCompiler", args=args
            )
            if result != 0:
                raise TaskError("Wire compiler exited non-zero ({0})".format(result))
Beispiel #6
0
    def format_args_for_target(self, target):
        """Calculate the arguments to pass to the command line for a single target."""
        sources_by_base = self._calculate_sources([target])
        if self.codegen_strategy.name() == 'isolated':
            sources = OrderedSet(target.sources_relative_to_buildroot())
        else:
            sources = OrderedSet(
                itertools.chain.from_iterable(sources_by_base.values()))
        if not self.validate_sources_present(sources, [target]):
            return None
        relative_sources = OrderedSet()
        for source in sources:
            source_root = SourceRoot.find_by_path(source)
            if not source_root:
                source_root = SourceRoot.find(target)
            relative_source = os.path.relpath(source, source_root)
            relative_sources.add(relative_source)
        check_duplicate_conflicting_protos(self, sources_by_base,
                                           relative_sources, self.context.log)

        args = ['--java_out={0}'.format(self.codegen_workdir(target))]

        # Add all params in payload to args

        if target.payload.get_field_value('no_options'):
            args.append('--no_options')

        def append_service_opts(service_type_name, service_type_value,
                                options_values):
            """Append --service_writer or --service_factory args as appropriate.

      :param str service_type_name: the target parameter/option prefix
      :param str service_type_value: class passed to the --service_x= option
      :param list options_values: string options to be passed with --service_x_opt
      """
            if service_type_value:
                args.append('--{0}={1}'.format(service_type_name,
                                               service_type_value))
                if options_values:
                    for opt in options_values:
                        args.append('--{0}_opt'.format(service_type_name))
                        args.append(opt)

        # A check is done in the java_wire_library target  to make sure only one of --service_writer or
        # --service_factory is specified.
        if self.wire_compiler_version < Revision(2, 0):
            if target.payload.service_factory:
                raise TaskError(
                    '{spec} used service_factory, which is not available before Wire 2.0. You '
                    'should use service_writer instead.'.format(
                        spec=target.address.spec))
            append_service_opts('service_writer',
                                target.payload.service_writer,
                                target.payload.service_writer_options)
        else:
            if target.payload.service_writer:
                raise TaskError(
                    '{spec} used service_writer, which is not available after Wire 2.0. You '
                    'should use service_factory instead.'.format(
                        spec=target.address.spec))
            append_service_opts('service_factory',
                                target.payload.service_factory,
                                target.payload.service_factory_options)

        registry_class = target.payload.registry_class
        if registry_class:
            args.append('--registry_class={0}'.format(registry_class))

        if target.payload.roots:
            args.append('--roots={0}'.format(','.join(target.payload.roots)))

        if target.payload.enum_options:
            args.append('--enum_options={0}'.format(','.join(
                target.payload.enum_options)))

        if self.wire_compiler_version < Revision(2, 0):
            args.append('--proto_path={0}'.format(
                os.path.join(get_buildroot(), SourceRoot.find(target))))
        else:
            # NB(gmalmquist): Support for multiple --proto_paths was introduced in Wire 2.0.
            for path in self._calculate_proto_paths(target):
                args.append('--proto_path={0}'.format(path))

        args.extend(relative_sources)
        return args
Beispiel #7
0
    def format_args_for_target(self, target):
        """Calculate the arguments to pass to the command line for a single target."""
        sources_by_base = self._calculate_sources([target])
        if self.codegen_strategy.name() == "isolated":
            sources = OrderedSet(target.sources_relative_to_buildroot())
        else:
            sources = OrderedSet(itertools.chain.from_iterable(sources_by_base.values()))
        if not self.validate_sources_present(sources, [target]):
            return None
        relative_sources = OrderedSet()
        for source in sources:
            source_root = SourceRoot.find_by_path(source)
            if not source_root:
                source_root = SourceRoot.find(target)
            relative_source = os.path.relpath(source, source_root)
            relative_sources.add(relative_source)
        check_duplicate_conflicting_protos(self, sources_by_base, relative_sources, self.context.log)

        args = ["--java_out={0}".format(self.codegen_workdir(target))]

        # Add all params in payload to args

        if target.payload.get_field_value("no_options"):
            args.append("--no_options")

        def append_service_opts(service_type_name, service_type_value, options_values):
            """Append --service_writer or --service_factory args as appropriate.

      :param str service_type_name: the target parameter/option prefix
      :param str service_type_value: class passed to the --service_x= option
      :param list options_values: string options to be passed with --service_x_opt
      """
            if service_type_value:
                args.append("--{0}={1}".format(service_type_name, service_type_value))
                if options_values:
                    for opt in options_values:
                        args.append("--{0}_opt".format(service_type_name))
                        args.append(opt)

        # A check is done in the java_wire_library target  to make sure only one of --service_writer or
        # --service_factory is specified.
        if self.wire_compiler_version < Revision(2, 0):
            if target.payload.service_factory:
                raise TaskError(
                    "{spec} used service_factory, which is not available before Wire 2.0. You "
                    "should use service_writer instead.".format(spec=target.address.spec)
                )
            append_service_opts("service_writer", target.payload.service_writer, target.payload.service_writer_options)
        else:
            if target.payload.service_writer:
                raise TaskError(
                    "{spec} used service_writer, which is not available after Wire 2.0. You "
                    "should use service_factory instead.".format(spec=target.address.spec)
                )
            append_service_opts(
                "service_factory", target.payload.service_factory, target.payload.service_factory_options
            )

        registry_class = target.payload.registry_class
        if registry_class:
            args.append("--registry_class={0}".format(registry_class))

        if target.payload.roots:
            args.append("--roots={0}".format(",".join(target.payload.roots)))

        if target.payload.enum_options:
            args.append("--enum_options={0}".format(",".join(target.payload.enum_options)))

        if self.wire_compiler_version < Revision(2, 0):
            args.append("--proto_path={0}".format(os.path.join(get_buildroot(), SourceRoot.find(target))))
        else:
            # NB(gmalmquist): Support for multiple --proto_paths was introduced in Wire 2.0.
            for path in self._calculate_proto_paths(target):
                args.append("--proto_path={0}".format(path))

        args.extend(relative_sources)
        return args