Compare commits

...

33 Commits

Author SHA1 Message Date
Renovate Bot
d75e519d8f Update module github.com/prometheus/client_model to v0.6.1 2024-06-03 22:03:22 +00:00
4a86315749 Merge pull request 'Update golang Docker tag to v1.22' (#3) from renovate/golang-1.x into master
Reviewed-on: #3
2024-06-03 23:58:54 +02:00
Renovate Bot
882544647e Update golang Docker tag to v1.22 2024-06-03 21:56:31 +00:00
fbe8435884 Merge pull request 'Configure Renovate' (#1) from renovate/configure into master
Reviewed-on: #1
2024-06-03 23:37:03 +02:00
Renovate Bot
3b5bce2a65 Add renovate.json 2024-06-03 21:35:53 +00:00
Rasmus Lauritsen
d2eb9e8498 Updated MQ 2023-09-10 19:38:24 +02:00
d8ee2d131a Update docs 2023-07-03 22:57:38 +02:00
bbb056f38c Added binaries 2023-07-03 22:24:47 +02:00
Arthur Barr
e657c5eb56 Add doc for MQ Advanced for Developers on arm64 (#528) 2023-06-29 16:33:21 +01:00
arthur.barr@uk.ibm.com
3599852fc1 Include timestamp in test output for JSON logs
For a failing test, JSON log output from a container is abridged to just include the message text.  This change adds the timestamp as well.
2023-06-05 09:48:19 +01:00
arthur.barr@uk.ibm.com
05fe51d96d Only use coverage options when necessary 2023-06-05 09:48:19 +01:00
Avinash Ganesh
1f7334e3d1 To fix web server logs' header missing issue (#424)
* Fix for issue

* Tests case added

* Update main.go

Keep the mirror code ready before web server comes up and would start logging. For this, moved the postInit() function call after checkLogSourceForMirroring("web").

* Updates post review meeting

* Update docker_api_test.go

To fix travis build error

* Comment altered
2023-06-01 17:23:50 +05:30
Tom Jefferson
dfa8e1ba41 Merge pull request #446 from mq-cloudpak/tadj-go-update
Update go version (master)
2023-05-25 15:43:42 +01:00
Tom Jefferson
9a8582a7a9 Update go version (master) 2023-05-25 14:30:39 +01:00
Tom Jefferson
57ffe4011d Merge pull request #441 from mq-cloudpak/tadj-update-go-mod-master
Update go mod to 1.19
2023-05-18 09:32:56 +01:00
Tom Jefferson
1d60dd7ce5 Update go mod to 1.19 2023-05-17 15:35:38 +01:00
Tom Jefferson
dc71321648 Merge pull request #436 from mq-cloudpak/tadj-update-go-master
Update GO and UBI (master)
2023-05-17 13:24:15 +01:00
Tom Jefferson
bc4f246a75 Update GO and UBI (master) 2023-05-17 10:56:06 +01:00
Tom Jefferson
cc619bdd86 Merge pull request #431 from mq-cloudpak/tadj-update-go-master
Update go version (master)
2023-05-05 12:29:54 +01:00
Tom Jefferson
784f03875e Update go version (master) 2023-05-05 09:56:38 +01:00
Tom Jefferson
1b7dd14555 Merge pull request #428 from mq-cloudpak/tadj-update-go-master
Update go version
2023-05-04 12:52:24 +01:00
Tom Jefferson
91603a08b0 Update go version 2023-05-04 11:34:37 +01:00
Alec Painter
1766663a78 Merge pull request #421 from mq-cloudpak/ahp-april-ubi-updates
updated missed go version
2023-04-11 15:55:15 +01:00
Alec-Painter
8ca5f31853 updated missed go version 2023-04-11 12:55:41 +01:00
Alec Painter
447e1c57ce Merge pull request #420 from mq-cloudpak/ahp-april-ubi-updates
Updated go-tools & UBI
2023-04-11 12:33:06 +01:00
Alec-Painter
0e95c1ca9e Updated go-tools & UBI 2023-04-11 08:31:22 +01:00
Nicholas Daffern
7d093b4340 Increase timeout in Container tests for qmgr to become ready (#417)
Signed-off-by: Nicholas-Daffern <Nicholas.Daffern@ibm.com>
2023-04-03 10:03:08 +01:00
Nicholas Daffern
33566bed16 Use Podman and Docker CLI for Container tests instead of Docker API (#415)
Signed-off-by: Nicholas-Daffern <Nicholas.Daffern@ibm.com>
2023-03-30 09:44:39 +01:00
Tom Jefferson
e14ffb261a Merge pull request #414 from mq-cloudpak/tadj-march-update-master
Update go and ubi versions
2023-03-08 11:01:18 +00:00
Tom Jefferson
1d239647f4 Update go and ubi versions 2023-03-08 09:51:09 +00:00
Stephen Marshall
f10e2facf8 Update licenses for MQ 9.3.3 2023-03-06 16:21:06 +00:00
arthur.barr@uk.ibm.com
bad1cfaa96 Use JRE that comes with with MQ on ARM 2023-02-23 16:30:49 +00:00
Stephen Marshall
bddb9bfd3a Update to MQ 9.3.3.0 2023-02-21 18:49:00 +00:00
153 changed files with 14202 additions and 4007 deletions

2
.gitignore vendored
View File

@@ -6,7 +6,7 @@ test/docker/vendor
test/kubernetes/vendor test/kubernetes/vendor
build build
coverage coverage
downloads #downloads
incubating/mqipt/ms81* incubating/mqipt/ms81*
vendor/github.com/prometheus/client_model/bin/ vendor/github.com/prometheus/client_model/bin/
vendor/github.com/prometheus/client_model/.classpath vendor/github.com/prometheus/client_model/.classpath

View File

@@ -18,7 +18,7 @@ sudo: required
language: go language: go
go: go:
- "1.18.9" - "1.19.9"
services: services:
- docker - docker
@@ -42,7 +42,7 @@ jobs:
name: "Basic AMD64 build" name: "Basic AMD64 build"
os: linux os: linux
env: env:
- MQ_ARCHIVE_REPOSITORY_DEV=$MQ_932_ARCHIVE_REPOSITORY_DEV_AMD64 - MQ_ARCHIVE_REPOSITORY_DEV=$MQ_933_ARCHIVE_REPOSITORY_DEV_AMD64
script: bash -e travis-build-scripts/run.sh script: bash -e travis-build-scripts/run.sh
# CD Build # CD Build
@@ -58,8 +58,8 @@ jobs:
os: linux os: linux
env: env:
- BUILD_ALL=true - BUILD_ALL=true
- MQ_ARCHIVE_REPOSITORY=$MQ_932_ARCHIVE_REPOSITORY_AMD64 - MQ_ARCHIVE_REPOSITORY=$MQ_933_ARCHIVE_REPOSITORY_AMD64
- MQ_ARCHIVE_REPOSITORY_DEV=$MQ_932_ARCHIVE_REPOSITORY_DEV_AMD64 - MQ_ARCHIVE_REPOSITORY_DEV=$MQ_933_ARCHIVE_REPOSITORY_DEV_AMD64
script: bash -e travis-build-scripts/run.sh script: bash -e travis-build-scripts/run.sh
- stage: build - stage: build
if: branch = private-master OR tag =~ ^release-candidate* if: branch = private-master OR tag =~ ^release-candidate*
@@ -68,8 +68,8 @@ jobs:
env: env:
- BUILD_ALL=true - BUILD_ALL=true
- TEST_OPTS_DOCKER="-run TestGoldenPathWithMetrics" - TEST_OPTS_DOCKER="-run TestGoldenPathWithMetrics"
- MQ_ARCHIVE_REPOSITORY=$MQ_932_ARCHIVE_REPOSITORY_S390X - MQ_ARCHIVE_REPOSITORY=$MQ_933_ARCHIVE_REPOSITORY_S390X
- MQ_ARCHIVE_REPOSITORY_DEV=$MQ_932_ARCHIVE_REPOSITORY_DEV_S390X - MQ_ARCHIVE_REPOSITORY_DEV=$MQ_933_ARCHIVE_REPOSITORY_DEV_S390X
script: bash -e travis-build-scripts/run.sh script: bash -e travis-build-scripts/run.sh
- stage: build - stage: build
if: branch = private-master OR tag =~ ^release-candidate* if: branch = private-master OR tag =~ ^release-candidate*
@@ -78,8 +78,8 @@ jobs:
env: env:
- BUILD_ALL=true - BUILD_ALL=true
- TEST_OPTS_DOCKER="-run TestGoldenPathWithMetrics" - TEST_OPTS_DOCKER="-run TestGoldenPathWithMetrics"
- MQ_ARCHIVE_REPOSITORY=$MQ_932_ARCHIVE_REPOSITORY_PPC64LE - MQ_ARCHIVE_REPOSITORY=$MQ_933_ARCHIVE_REPOSITORY_PPC64LE
- MQ_ARCHIVE_REPOSITORY_DEV=$MQ_932_ARCHIVE_REPOSITORY_DEV_PPC64LE - MQ_ARCHIVE_REPOSITORY_DEV=$MQ_933_ARCHIVE_REPOSITORY_DEV_PPC64LE
script: bash -e travis-build-scripts/run.sh script: bash -e travis-build-scripts/run.sh
- stage: push-manifest - stage: push-manifest
if: branch = private-master AND type != pull_request OR tag =~ ^release-candidate* if: branch = private-master AND type != pull_request OR tag =~ ^release-candidate*

39
CBO.md Normal file
View File

@@ -0,0 +1,39 @@
# MQ in Docker
## Download new version
Download IBM MQ Advanced for Developers here: https://public.dhe.ibm.com/ibmdl/export/pub/software/websphere/messaging/mqadv/
Place the file in the downloads folder of this repo.
```bash
mkdir -p downloads
wget -P downloads https://public.dhe.ibm.com/ibmdl/export/pub/software/websphere/messaging/mqadv/9.3.3.1-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxX64.tar.gz
wget -P downloads https://public.dhe.ibm.com/ibmdl/export/pub/software/websphere/messaging/mqadv/9.3.3.1-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxARM64.tar.gz
```
# Build Docker image
Update ```MQ_ARCHIVE``` with the new filename in the two Dockerfiles
```bash
nano Dockerfile-server-arm
nano Dockerfile-server-x64
```
Build the new images
```bash
docker buildx build -t <tag> -f <dockerfile> .
# Build for various architechtures
docker buildx build --platform linux/amd64 -t git.cbo.dk/academy/mq:9.3.3.1-amd64 -f Dockerfile-server-x64 .
docker buildx build --platform linux/arm64 -t git.cbo.dk/academy/mq:9.3.3.1-arm64 -f Dockerfile-server-arm .
docker image tag git.cbo.dk/academy/mq:9.3.3.1-amd64 git.cbo.dk/academy/mq:latest
# Push to registry (Optional)
docker login git.cbo.dk
docker push --all-tags git.cbo.dk/academy/mq
```
# Deploy MQ
```bash
docker stop ibmmq
docker rm ibmmq
docker run --name "ibmmq" -d -p 1414:1414 -p 9157:9157 -p 9443:9443 -e LICENSE=accept -e MQ_ADMIN_PASSWORD=passw0rd -e MQ_QMGR_NAME=MQDOCKER -e MQ_ENABLE_METRICS=true --name ibmmq git.cbo.dk/academy/mq:latest
```

View File

@@ -1,5 +1,9 @@
# Change log # Change log
## 9.3.3.0 (2023-06)
* Updated to MQ version 9.3.3.0
## 9.3.2.0 (2023-02) ## 9.3.2.0 (2023-02)
* Updated to MQ version 9.3.2.0 * Updated to MQ version 9.3.2.0

210
Dockerfile-server-arm Normal file
View File

@@ -0,0 +1,210 @@
# © Copyright IBM Corporation 2015, 2023
#
# 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
#
# http://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.
# Download IBM MQ Advanced for Developers here: https://public.dhe.ibm.com/ibmdl/export/pub/software/websphere/messaging/mqadv/
# mkdir downloads
# Kopier 9.3.3.0-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxARM64.tar.gz ind i downloads.
# Opdater .dockerignore
# docker build -t mqserver -f Dockerfile-server-arm .
# docker run -d -p 1414:1414 -p 9157:9157 -p 9443:9443 -e LICENSE=accept --name mqserver mqserver
ARG BASE_IMAGE=registry.access.redhat.com/ubi8/ubi-minimal
ARG BASE_TAG=8.8-860
ARG BUILDER_IMAGE=registry.access.redhat.com/ubi8/go-toolset
ARG BUILDER_TAG=1.19.9-2
ARG GO_WORKDIR=/opt/app-root/src/go/src/github.com/ibm-messaging/mq-container
ARG MQ_ARCHIVE="downloads/9.3.3.1-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxARM64.tar.gz"
###############################################################################
# Build stage to build Go code
###############################################################################
FROM $BUILDER_IMAGE:$BUILDER_TAG as builder
ARG IMAGE_REVISION="Not specified"
ARG IMAGE_SOURCE="Not specified"
ARG IMAGE_TAG="Not specified"
ARG GO_WORKDIR
ARG MQ_ARCHIVE
USER 0
WORKDIR $GO_WORKDIR/
ADD $MQ_ARCHIVE /opt/mqm
ENV CGO_CFLAGS="-I/opt/mqm/inc/" \
CGO_LDFLAGS_ALLOW="-Wl,-rpath.*" \
PATH="${PATH}:/opt/mqm/bin"
COPY go.mod go.sum ./
COPY cmd/ ./cmd
COPY internal/ ./internal
COPY pkg/ ./pkg
COPY vendor/ ./vendor
RUN go build -ldflags "-X \"main.ImageCreated=$(date --iso-8601=seconds)\" -X \"main.ImageRevision=$IMAGE_REVISION\" -X \"main.ImageSource=$IMAGE_SOURCE\" -X \"main.ImageTag=$IMAGE_TAG\"" ./cmd/runmqserver/ \
&& go build ./cmd/chkmqready/ \
&& go build ./cmd/chkmqhealthy/ \
&& go build ./cmd/chkmqstarted/ \
&& go build ./cmd/runmqdevserver/ \
&& go test -v ./cmd/runmqdevserver/... \
&& go test -v ./cmd/runmqserver/ \
&& go test -v ./cmd/chkmqready/ \
&& go test -v ./cmd/chkmqhealthy/ \
&& go test -v ./cmd/chkmqstarted/ \
&& go test -v ./pkg/... \
&& go test -v ./internal/... \
&& go vet ./cmd/... ./internal/...
###############################################################################
# Build stage to reduce MQ packages included using genmqpkg
###############################################################################
FROM $BASE_IMAGE:$BASE_TAG AS mq-redux
ARG BASE_IMAGE
ARG BASE_TAG
ARG MQ_ARCHIVE
WORKDIR /tmp/mq
ENV genmqpkg_inc32=0 \
genmqpkg_incadm=1 \
genmqpkg_incamqp=0 \
genmqpkg_incams=1 \
genmqpkg_inccbl=0 \
genmqpkg_inccics=0 \
genmqpkg_inccpp=0 \
genmqpkg_incdnet=0 \
genmqpkg_incjava=1 \
genmqpkg_incjre=1 \
genmqpkg_incman=0 \
genmqpkg_incmqbc=0 \
genmqpkg_incmqft=0 \
genmqpkg_incmqsf=0 \
genmqpkg_incmqxr=0 \
genmqpkg_incnls=1 \
genmqpkg_incras=1 \
genmqpkg_incsamp=1 \
genmqpkg_incsdk=0 \
genmqpkg_inctls=1 \
genmqpkg_incunthrd=0 \
genmqpkg_incweb=1
ADD $MQ_ARCHIVE /opt/mqm-noinstall
# Run genmqpkg to reduce the MQ packages included
RUN /opt/mqm-noinstall/bin/genmqpkg.sh -b /opt/mqm-redux
###############################################################################
# Main build stage, to build MQ image
###############################################################################
FROM $BASE_IMAGE:$BASE_TAG AS mq-server
ARG MQ_URL
ARG BASE_IMAGE
ARG BASE_TAG
ARG GO_WORKDIR
LABEL summary="IBM MQ Advanced Server" \
description="Simplify, accelerate and facilitate the reliable exchange of data with a security-rich messaging solution — trusted by the worlds most successful enterprises" \
vendor="IBM" \
maintainer="IBM" \
distribution-scope="private" \
authoritative-source-url="https://www.ibm.com/software/passportadvantage/" \
url="https://www.ibm.com/products/mq/advanced" \
io.openshift.tags="mq messaging" \
io.k8s.display-name="IBM MQ Advanced Server" \
io.k8s.description="Simplify, accelerate and facilitate the reliable exchange of data with a security-rich messaging solution — trusted by the worlds most successful enterprises" \
base-image=$BASE_IMAGE \
base-image-release=$BASE_TAG
COPY --from=mq-redux /opt/mqm-redux/ /opt/mqm/
COPY setup-image.sh /usr/local/bin/
COPY install-mq-server-prereqs.sh /usr/local/bin/
RUN env \
&& chmod u+x /usr/local/bin/install-*.sh \
&& chmod u+x /usr/local/bin/setup-image.sh \
&& install-mq-server-prereqs.sh \
&& setup-image.sh \
&& /opt/mqm/bin/security/amqpamcf \
&& chown -R 1001:root /opt/mqm/*
COPY --from=builder $GO_WORKDIR/runmqserver /usr/local/bin/
COPY --from=builder $GO_WORKDIR/chkmq* /usr/local/bin/
COPY NOTICES.txt /opt/mqm/licenses/notices-container.txt
COPY ha/native-ha.ini.tpl /etc/mqm/native-ha.ini.tpl
# Copy web XML files
COPY web /etc/mqm/web
COPY etc/mqm/*.tpl /etc/mqm/
RUN chmod ug+x /usr/local/bin/runmqserver \
&& chown 1001:root /usr/local/bin/*mq* \
&& chmod ug+x /usr/local/bin/chkmq* \
&& chown -R 1001:root /etc/mqm/* \
&& install --directory --mode 2775 --owner 1001 --group root /run/runmqserver \
&& touch /run/termination-log \
&& chown 1001:root /run/termination-log \
&& chmod 0660 /run/termination-log \
&& chmod -R g+w /etc/mqm/web
# Always use port 1414 for MQ & 9157 for the metrics
EXPOSE 1414 9157 9443
ENV MQ_OVERRIDE_DATA_PATH=/mnt/mqm/data MQ_OVERRIDE_INSTALLATION_NAME=Installation1 MQ_USER_NAME="mqm" PATH="${PATH}:/opt/mqm/bin"
ENV MQ_GRACE_PERIOD=30
ENV LANG=en_US.UTF-8 AMQ_DIAGNOSTIC_MSG_SEVERITY=1 AMQ_ADDITIONAL_JSON_LOG=1
ENV MQ_LOGGING_CONSOLE_EXCLUDE_ID=AMQ5041I,AMQ5052I,AMQ5051I,AMQ5037I,AMQ5975I
ENV WLP_LOGGING_MESSAGE_FORMAT=json
# We can run as any UID
USER 1001
ENV MQ_CONNAUTH_USE_HTP=false
ENTRYPOINT ["runmqserver"]
###############################################################################
# Build stage to build C code for custom authorization service (developer-only)
###############################################################################
# Use the Go toolset image, which already includes gcc and the MQ SDK
FROM builder as cbuilder
USER 0
# Install the Apache Portable Runtime code (used for htpasswd hash checking)
RUN yum --assumeyes --disableplugin=subscription-manager install apr-devel apr-util-openssl apr-util-devel
COPY authservice/ /opt/app-root/src/authservice/
WORKDIR /opt/app-root/src/authservice/mqhtpass
RUN make all
###############################################################################
# Add default developer config
###############################################################################
FROM mq-server AS mq-dev-server
ARG BASE_IMAGE
ARG BASE_TAG
ARG GO_WORKDIR
LABEL summary="IBM MQ Advanced for Developers Server" \
description="Simplify, accelerate and facilitate the reliable exchange of data with a security-rich messaging solution — trusted by the worlds most successful enterprises" \
vendor="IBM" \
distribution-scope="private" \
authoritative-source-url="https://www.ibm.com/software/passportadvantage/" \
url="https://www.ibm.com/products/mq/advanced" \
io.openshift.tags="mq messaging" \
io.k8s.display-name="IBM MQ Advanced for Developers Server" \
io.k8s.description="Simplify, accelerate and facilitate the reliable exchange of data with a security-rich messaging solution — trusted by the worlds most successful enterprises" \
base-image=$BASE_IMAGE \
base-image-release=$BASE_TAG
USER 0
COPY --from=cbuilder /opt/app-root/src/authservice/mqhtpass/build/mqhtpass.so /opt/mqm/lib64/
COPY etc/mqm/*.ini /etc/mqm/
COPY etc/mqm/mq.htpasswd /etc/mqm/
COPY incubating/mqadvanced-server-dev/install-extra-packages.sh /usr/local/bin/
RUN chmod u+x /usr/local/bin/install-extra-packages.sh \
&& sleep 1 \
&& install-extra-packages.sh
COPY --from=builder $GO_WORKDIR/runmqdevserver /usr/local/bin/
# Copy template files
COPY incubating/mqadvanced-server-dev/*.tpl /etc/mqm/
# Copy web XML files for default developer configuration
COPY incubating/mqadvanced-server-dev/web /etc/mqm/web
RUN chown -R 1001:root /etc/mqm/* \
&& chmod -R g+w /etc/mqm/web \
&& chmod +x /usr/local/bin/runmq* \
&& chmod 0660 /etc/mqm/mq.htpasswd \
&& install --directory --mode 2775 --owner 1001 --group root /run/runmqdevserver
ENV MQ_DEV=true \
MQ_ENABLE_EMBEDDED_WEB_SERVER=1 \
MQ_GENERATE_CERTIFICATE_HOSTNAME=localhost \
LD_LIBRARY_PATH=/opt/mqm/lib64 \
MQ_CONNAUTH_USE_HTP=true \
MQS_PERMIT_UNKNOWN_ID=true
USER 1001
ENTRYPOINT ["runmqdevserver"]

View File

@@ -12,12 +12,19 @@
# See the License for the specific language governing permissions and # See the License for the specific language governing permissions and
# limitations under the License. # limitations under the License.
# Download IBM MQ Advanced for Developers here: https://public.dhe.ibm.com/ibmdl/export/pub/software/websphere/messaging/mqadv/
# mkdir downloads
# Kopier 9.3.3.0-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxX64.tar.gz ind i downloads.
# Opdater .dockerignore
# docker build -t mqserver -f Dockerfile-server-x64 .
# docker run -d -p 1414:1414 -p 9157:9157 -p 9443:9443 -e LICENSE=accept --name mqserver mqserver
ARG BASE_IMAGE=registry.access.redhat.com/ubi8/ubi-minimal ARG BASE_IMAGE=registry.access.redhat.com/ubi8/ubi-minimal
ARG BASE_TAG=8.7-1049.1675784874 ARG BASE_TAG=8.8-860
ARG BUILDER_IMAGE=registry.access.redhat.com/ubi8/go-toolset ARG BUILDER_IMAGE=registry.access.redhat.com/ubi8/go-toolset
ARG BUILDER_TAG=1.18.9-8.1675807488 ARG BUILDER_TAG=1.19.9-2
ARG GO_WORKDIR=/opt/app-root/src/go/src/github.com/ibm-messaging/mq-container ARG GO_WORKDIR=/opt/app-root/src/go/src/github.com/ibm-messaging/mq-container
ARG MQ_ARCHIVE="downloads/9.3.2.0-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxX64.tar.gz" ARG MQ_ARCHIVE="downloads/9.3.3.0-IBM-MQ-Advanced-for-Developers-Non-Install-LinuxX64.tar.gz"
############################################################################### ###############################################################################
# Build stage to build Go code # Build stage to build Go code

View File

@@ -15,7 +15,7 @@
ARG BASE_IMAGE ARG BASE_IMAGE
# Build stage to build Go code # Build stage to build Go code
FROM golang:1.10 as builder FROM golang:1.22 as builder
WORKDIR /go/src/github.com/ibm-messaging/mq-container/ WORKDIR /go/src/github.com/ibm-messaging/mq-container/
COPY cmd/ ./cmd COPY cmd/ ./cmd
COPY internal/ ./internal COPY internal/ ./internal

View File

@@ -45,10 +45,10 @@ MQ_ARCHIVE ?= IBM_MQ_$(MQ_VERSION_VRM)_$(MQ_ARCHIVE_TYPE)_$(MQ_ARCHIVE_ARCH)_NOI
MQ_ARCHIVE_DEV ?= $(MQ_VERSION)-IBM-MQ-Advanced-for-Developers-Non-Install-$(MQ_ARCHIVE_DEV_TYPE)$(MQ_ARCHIVE_DEV_ARCH).tar.gz MQ_ARCHIVE_DEV ?= $(MQ_VERSION)-IBM-MQ-Advanced-for-Developers-Non-Install-$(MQ_ARCHIVE_DEV_TYPE)$(MQ_ARCHIVE_DEV_ARCH).tar.gz
# MQ_SDK_ARCHIVE specifies the archive to use for building the golang programs. Defaults vary on developer or advanced. # MQ_SDK_ARCHIVE specifies the archive to use for building the golang programs. Defaults vary on developer or advanced.
MQ_SDK_ARCHIVE ?= $(MQ_ARCHIVE_DEV_$(MQ_VERSION)) MQ_SDK_ARCHIVE ?= $(MQ_ARCHIVE_DEV_$(MQ_VERSION))
# Options to `go test` for the Docker tests # Options to `go test` for the Container tests
TEST_OPTS_DOCKER ?= TEST_OPTS_CONTAINER ?=
# Timeout for the Docker tests # Timeout for the tests
TEST_TIMEOUT_DOCKER ?= 45m TEST_TIMEOUT_CONTAINER ?= 45m
# MQ_IMAGE_ADVANCEDSERVER is the name of the built MQ Advanced image # MQ_IMAGE_ADVANCEDSERVER is the name of the built MQ Advanced image
MQ_IMAGE_ADVANCEDSERVER ?=ibm-mqadvanced-server MQ_IMAGE_ADVANCEDSERVER ?=ibm-mqadvanced-server
# MQ_IMAGE_DEVSERVER is the name of the built MQ Advanced for Developers image # MQ_IMAGE_DEVSERVER is the name of the built MQ Advanced for Developers image
@@ -278,9 +278,9 @@ cache-mq-tag:
# Test targets # Test targets
############################################################################### ###############################################################################
# Vendor Go dependencies for the Docker tests # Vendor Go dependencies for the Container tests
test/docker/vendor: test/container/vendor:
cd test/docker && go mod vendor cd test/container && go mod vendor
# Shortcut to just run the unit tests # Shortcut to just run the unit tests
.PHONY: test-unit .PHONY: test-unit
@@ -288,28 +288,28 @@ test-unit:
$(COMMAND) build --target builder --file Dockerfile-server . $(COMMAND) build --target builder --file Dockerfile-server .
.PHONY: test-advancedserver .PHONY: test-advancedserver
test-advancedserver: test/docker/vendor test-advancedserver: test/container/vendor
$(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) on $(shell $(COMMAND) --version)"$(END))) $(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) on $(shell $(COMMAND) --version)"$(END)))
$(COMMAND) inspect $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) $(COMMAND) inspect $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG)
cd test/docker && TEST_IMAGE=$(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) EXPECTED_LICENSE=Production DOCKER_API_VERSION=$(DOCKER_API_VERSION) go test -parallel $(NUM_CPU) -timeout $(TEST_TIMEOUT_DOCKER) $(TEST_OPTS_DOCKER) cd test/container && TEST_IMAGE=$(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) EXPECTED_LICENSE=Production DOCKER_API_VERSION=$(DOCKER_API_VERSION) COMMAND=$(COMMAND) go test -parallel $(NUM_CPU) -timeout $(TEST_TIMEOUT_CONTAINER) $(TEST_OPTS_CONTAINER)
.PHONY: build-devjmstest .PHONY: build-devjmstest
build-devjmstest: build-devjmstest:
$(info $(SPACER)$(shell printf $(TITLE)"Build JMS tests for developer config"$(END))) $(info $(SPACER)$(shell printf $(TITLE)"Build JMS tests for developer config"$(END)))
cd test/messaging && docker build --tag $(DEV_JMS_IMAGE) . cd test/messaging && $(COMMAND) build --tag $(DEV_JMS_IMAGE) .
.PHONY: test-devserver .PHONY: test-devserver
test-devserver: test/docker/vendor test-devserver: test/container/vendor
$(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_DEVSERVER):$(MQ_TAG) on $(shell $(COMMAND) --version)"$(END))) $(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_DEVSERVER):$(MQ_TAG) on $(shell $(COMMAND) --version)"$(END)))
$(COMMAND) inspect $(MQ_IMAGE_DEVSERVER):$(MQ_TAG) $(COMMAND) inspect $(MQ_IMAGE_DEVSERVER):$(MQ_TAG)
cd test/docker && TEST_IMAGE=$(MQ_IMAGE_DEVSERVER):$(MQ_TAG) EXPECTED_LICENSE=Developer DEV_JMS_IMAGE=$(DEV_JMS_IMAGE) IBMJRE=false DOCKER_API_VERSION=$(DOCKER_API_VERSION) go test -parallel $(NUM_CPU) -timeout $(TEST_TIMEOUT_DOCKER) -tags mqdev $(TEST_OPTS_DOCKER) cd test/container && TEST_IMAGE=$(MQ_IMAGE_DEVSERVER):$(MQ_TAG) EXPECTED_LICENSE=Developer DEV_JMS_IMAGE=$(DEV_JMS_IMAGE) IBMJRE=false DOCKER_API_VERSION=$(DOCKER_API_VERSION) COMMAND=$(COMMAND) go test -parallel $(NUM_CPU) -timeout $(TEST_TIMEOUT_CONTAINER) -tags mqdev $(TEST_OPTS_CONTAINER)
.PHONY: coverage .PHONY: coverage
coverage: coverage:
mkdir coverage mkdir coverage
.PHONY: test-advancedserver-cover .PHONY: test-advancedserver-cover
test-advancedserver-cover: test/docker/vendor coverage test-advancedserver-cover: test/container/vendor coverage
$(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) with code coverage on $(shell $(COMMAND) --version)"$(END))) $(info $(SPACER)$(shell printf $(TITLE)"Test $(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG) with code coverage on $(shell $(COMMAND) --version)"$(END)))
rm -f ./coverage/unit*.cov rm -f ./coverage/unit*.cov
# Run unit tests with coverage, for each package under 'internal' # Run unit tests with coverage, for each package under 'internal'
@@ -319,16 +319,16 @@ test-advancedserver-cover: test/docker/vendor coverage
tail -q -n +2 ./coverage/unit-*.cov >> ./coverage/unit.cov tail -q -n +2 ./coverage/unit-*.cov >> ./coverage/unit.cov
go tool cover -html=./coverage/unit.cov -o ./coverage/unit.html go tool cover -html=./coverage/unit.cov -o ./coverage/unit.html
rm -f ./test/docker/coverage/*.cov rm -f ./test/container/coverage/*.cov
rm -f ./coverage/docker.* rm -f ./coverage/container.*
mkdir -p ./test/docker/coverage/ mkdir -p ./test/container/coverage/
cd test/docker && TEST_IMAGE=$(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG)-cover TEST_COVER=true DOCKER_API_VERSION=$(DOCKER_API_VERSION) go test $(TEST_OPTS_DOCKER) cd test/container && TEST_IMAGE=$(MQ_IMAGE_ADVANCEDSERVER):$(MQ_TAG)-cover TEST_COVER=true DOCKER_API_VERSION=$(DOCKER_API_VERSION) go test $(TEST_OPTS_CONTAINER)
echo 'mode: count' > ./coverage/docker.cov echo 'mode: count' > ./coverage/container.cov
tail -q -n +2 ./test/docker/coverage/*.cov >> ./coverage/docker.cov tail -q -n +2 ./test/container/coverage/*.cov >> ./coverage/container.cov
go tool cover -html=./coverage/docker.cov -o ./coverage/docker.html go tool cover -html=./coverage/container.cov -o ./coverage/container.html
echo 'mode: count' > ./coverage/combined.cov echo 'mode: count' > ./coverage/combined.cov
tail -q -n +2 ./coverage/unit.cov ./coverage/docker.cov >> ./coverage/combined.cov tail -q -n +2 ./coverage/unit.cov ./coverage/container.cov >> ./coverage/combined.cov
go tool cover -html=./coverage/combined.cov -o ./coverage/combined.html go tool cover -html=./coverage/combined.cov -o ./coverage/combined.html
############################################################################### ###############################################################################

View File

@@ -48,8 +48,8 @@ For issues relating specifically to the container image or Helm chart, please us
The Dockerfiles and associated code and scripts are licensed under the [Apache License 2.0](http://www.apache.org/licenses/LICENSE-2.0.html). The Dockerfiles and associated code and scripts are licensed under the [Apache License 2.0](http://www.apache.org/licenses/LICENSE-2.0.html).
Licenses for the products installed within the images are as follows: Licenses for the products installed within the images are as follows:
- [IBM MQ Advanced for Developers](http://www14.software.ibm.com/cgi-bin/weblap/lap.pl?la_formnum=Z125-3301-14&li_formnum=L-APIG-CAUEQC) (International License Agreement for Non-Warranted Programs). This license may be viewed from an image using the `LICENSE=view` environment variable as described above or by following the link above. - [IBM MQ Advanced for Developers](http://www14.software.ibm.com/cgi-bin/weblap/lap.pl?la_formnum=Z125-3301-14&li_formnum=L-AXAF-JLZ53A) (International License Agreement for Non-Warranted Programs). This license may be viewed from an image using the `LICENSE=view` environment variable as described above or by following the link above.
- [IBM MQ Advanced](http://www14.software.ibm.com/cgi-bin/weblap/lap.pl?la_formnum=Z125-3301-14&li_formnum=L-UPFX-8MW49T) (International Program License Agreement). This license may be viewed from an image using the `LICENSE=view` environment variable as described above or by following the link above. - [IBM MQ Advanced](http://www14.software.ibm.com/cgi-bin/weblap/lap.pl?la_formnum=Z125-3301-14&li_formnum=L-AMRD-XH6P3Q) (International Program License Agreement). This license may be viewed from an image using the `LICENSE=view` environment variable as described above or by following the link above.
Note: The IBM MQ Advanced for Developers license does not permit further distribution and the terms restrict usage to a developer machine. Note: The IBM MQ Advanced for Developers license does not permit further distribution and the terms restrict usage to a developer machine.

View File

@@ -211,7 +211,7 @@ func mirrorHTPasswdLogs(ctx context.Context, wg *sync.WaitGroup, name string, fr
// mirrorWebServerLogs starts a goroutine to mirror the contents of the Liberty web server messages.log // mirrorWebServerLogs starts a goroutine to mirror the contents of the Liberty web server messages.log
func mirrorWebServerLogs(ctx context.Context, wg *sync.WaitGroup, name string, fromStart bool, mf mirrorFunc) (chan error, error) { func mirrorWebServerLogs(ctx context.Context, wg *sync.WaitGroup, name string, fromStart bool, mf mirrorFunc) (chan error, error) {
return mirrorLog(ctx, wg, "/var/mqm/web/installations/Installation1/servers/mqweb/logs/messages.log", false, mf, true) return mirrorLog(ctx, wg, "/var/mqm/web/installations/Installation1/servers/mqweb/logs/messages.log", fromStart, mf, true)
} }
func getDebug() bool { func getDebug() bool {

View File

@@ -165,6 +165,27 @@ func doMain() error {
log.Println("One or more invalid value is provided for MQ_LOGGING_CONSOLE_SOURCE. Allowed values are 'qmgr' & 'web' in csv format") log.Println("One or more invalid value is provided for MQ_LOGGING_CONSOLE_SOURCE. Allowed values are 'qmgr' & 'web' in csv format")
} }
var wg sync.WaitGroup
defer func() {
log.Debug("Waiting for log mirroring to complete")
wg.Wait()
}()
ctx, cancelMirror := context.WithCancel(context.Background())
defer func() {
log.Debug("Cancel log mirroring")
cancelMirror()
}()
//For mirroring web server logs if source variable is set
if checkLogSourceForMirroring("web") {
// Always log from the end of the web server messages.log, because the log rotation should happen as soon as the web server starts
_, err = mirrorWebServerLogs(ctx, &wg, name, false, mf)
if err != nil {
logTermination(err)
return err
}
}
err = postInit(name, keyLabel, defaultP12Truststore) err = postInit(name, keyLabel, defaultP12Truststore)
if err != nil { if err != nil {
logTermination(err) logTermination(err)
@@ -205,17 +226,6 @@ func doMain() error {
} }
} }
var wg sync.WaitGroup
defer func() {
log.Debug("Waiting for log mirroring to complete")
wg.Wait()
}()
ctx, cancelMirror := context.WithCancel(context.Background())
defer func() {
log.Debug("Cancel log mirroring")
cancelMirror()
}()
//For mirroring mq system logs and qm logs, if environment variable is set //For mirroring mq system logs and qm logs, if environment variable is set
if checkLogSourceForMirroring("qmgr") { if checkLogSourceForMirroring("qmgr") {
//Mirror MQ system logs //Mirror MQ system logs
@@ -241,17 +251,6 @@ func doMain() error {
} }
} }
//For mirroring web server logs if source variable is set
if checkLogSourceForMirroring("web") {
// Always log from the start of the web server messages.log, as
// Liberty resets it.
_, err = mirrorWebServerLogs(ctx, &wg, name, true, mf)
if err != nil {
logTermination(err)
return err
}
}
err = updateCommandLevel() err = updateCommandLevel()
if err != nil { if err != nil {
logTermination(err) logTermination(err)

View File

@@ -1,6 +1,6 @@
########################################################################################################################################################### ###########################################################################################################################################################
# MQ_VERSION is the fully qualified MQ version number to build # MQ_VERSION is the fully qualified MQ version number to build
MQ_VERSION ?= 9.3.2.0 MQ_VERSION ?= 9.3.3.0
########################################################################################################################################################### ###########################################################################################################################################################

View File

@@ -38,7 +38,7 @@ However, if you wish to build the previous MQ LTS, use the [instructions](https:
## Building a developer image ## Building a developer image
Run `make build-devserver`, which will download the latest version of MQ Advanced for Developers from IBM developerWorks. This is currently only available on the `amd64` architecture. Run `make build-devserver`, which will download the latest version of MQ Advanced for Developers. This is available on the `amd64` and `arm64` (Apple Silicon) architectures.
You can use the environment variable `MQ_ARCHIVE_DEV` to specify an alternative local file to install from (which must be in the `downloads` directory). You can use the environment variable `MQ_ARCHIVE_DEV` to specify an alternative local file to install from (which must be in the `downloads` directory).

View File

@@ -16,5 +16,5 @@ docker run \
--env LICENSE=accept \ --env LICENSE=accept \
--env MQ_QMGR_NAME=QM1 \ --env MQ_QMGR_NAME=QM1 \
--detach \ --detach \
ibm-mqadvanced-server:9.3.2.0-amd64 ibm-mqadvanced-server:9.3.3.0-amd64
``` ```

View File

@@ -24,7 +24,7 @@ make test-advancedserver
You can specify the image to use directly by using the `MQ_IMAGE_ADVANCEDSERVER` or `MQ_IMAGE_DEVSERVER` variables, for example: You can specify the image to use directly by using the `MQ_IMAGE_ADVANCEDSERVER` or `MQ_IMAGE_DEVSERVER` variables, for example:
``` ```
MQ_IMAGE_ADVANCEDSERVER=ibm-mqadvanced-server:9.3.2.0-amd64 make test-advancedserver MQ_IMAGE_ADVANCEDSERVER=ibm-mqadvanced-server:9.3.3.0-amd64 make test-advancedserver
``` ```
You can pass parameters to `go test` with an environment variable. For example, to run the "TestGoldenPath" test, run the following command: You can pass parameters to `go test` with an environment variable. For example, to run the "TestGoldenPath" test, run the following command:

8
go.mod
View File

@@ -1,12 +1,12 @@
module github.com/ibm-messaging/mq-container module github.com/ibm-messaging/mq-container
go 1.18 go 1.19
require ( require (
github.com/genuinetools/amicontained v0.4.3 github.com/genuinetools/amicontained v0.4.3
github.com/ibm-messaging/mq-golang v2.0.0+incompatible github.com/ibm-messaging/mq-golang v2.0.0+incompatible
github.com/prometheus/client_golang v1.11.1 github.com/prometheus/client_golang v1.11.1
github.com/prometheus/client_model v0.2.0 github.com/prometheus/client_model v0.6.1
golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d golang.org/x/crypto v0.0.0-20220622213112-05595931fe9d
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1 golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1
software.sslmate.com/src/go-pkcs12 v0.0.0-20200830195227-52f69702a001 software.sslmate.com/src/go-pkcs12 v0.0.0-20200830195227-52f69702a001
@@ -15,10 +15,10 @@ require (
require ( require (
github.com/beorn7/perks v1.0.1 // indirect github.com/beorn7/perks v1.0.1 // indirect
github.com/cespare/xxhash/v2 v2.1.1 // indirect github.com/cespare/xxhash/v2 v2.1.1 // indirect
github.com/golang/protobuf v1.4.3 // indirect github.com/golang/protobuf v1.5.0 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.1 // indirect github.com/matttproud/golang_protobuf_extensions v1.0.1 // indirect
github.com/prometheus/common v0.26.0 // indirect github.com/prometheus/common v0.26.0 // indirect
github.com/prometheus/procfs v0.6.0 // indirect github.com/prometheus/procfs v0.6.0 // indirect
github.com/syndtr/gocapability v0.0.0-20200815063812-42c35b437635 // indirect github.com/syndtr/gocapability v0.0.0-20200815063812-42c35b437635 // indirect
google.golang.org/protobuf v1.26.0-rc.1 // indirect google.golang.org/protobuf v1.33.0 // indirect
) )

6
go.sum
View File

@@ -33,6 +33,8 @@ github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvq
github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
github.com/golang/protobuf v1.4.3 h1:JjCZWpVbqXDqFVmTfYWEVTMIYrL/NPdPSCHPJ0T/raM= github.com/golang/protobuf v1.4.3 h1:JjCZWpVbqXDqFVmTfYWEVTMIYrL/NPdPSCHPJ0T/raM=
github.com/golang/protobuf v1.4.3/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= github.com/golang/protobuf v1.4.3/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
github.com/golang/protobuf v1.5.0 h1:LUVKkCeviFUMKqHa4tXIIij/lbhnMbP7Fn5wKdKkRh4=
github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=
github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
@@ -75,6 +77,8 @@ github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:
github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
github.com/prometheus/client_model v0.2.0 h1:uq5h0d+GuxiXLJLNABMgp2qUWDPiLvgCzz2dUR+/W/M= github.com/prometheus/client_model v0.2.0 h1:uq5h0d+GuxiXLJLNABMgp2qUWDPiLvgCzz2dUR+/W/M=
github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.2.0/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
github.com/prometheus/client_model v0.6.1 h1:ZKSh/rekM+n3CeS952MLRAdFwIKqeY8b62p8ais2e9E=
github.com/prometheus/client_model v0.6.1/go.mod h1:OrxVMOVHjw3lKMa8+x6HeMGkHMQyHDk9E3jmP2AmGiY=
github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4=
github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo= github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo=
github.com/prometheus/common v0.26.0 h1:iMAkS2TDoNWnKM+Kopnx/8tnEStIfpYA0ur0xQzzhMQ= github.com/prometheus/common v0.26.0 h1:iMAkS2TDoNWnKM+Kopnx/8tnEStIfpYA0ur0xQzzhMQ=
@@ -137,6 +141,8 @@ google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzi
google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
google.golang.org/protobuf v1.26.0-rc.1 h1:7QnIQpGRHE5RnLKnESfDoxm2dTapTZua5a0kS0A+VXQ= google.golang.org/protobuf v1.26.0-rc.1 h1:7QnIQpGRHE5RnLKnESfDoxm2dTapTZua5a0kS0A+VXQ=
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
google.golang.org/protobuf v1.33.0 h1:uNO2rsAINq/JlFpSdYEKIZ0uKD/R9cpdv0T+yoGwGmI=
google.golang.org/protobuf v1.33.0/go.mod h1:c6P6GXX6sHbq/GpV6MGZEdwhWPcYBgnhAHhKbcUYpos=
gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw= gopkg.in/alecthomas/kingpin.v2 v2.2.6/go.mod h1:FMv+mEhP44yOT+4EoQTLFTRgOQ1FBLkstjWtayDeSgw=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=

View File

@@ -1,6 +1,6 @@
#!/bin/bash #!/bin/bash
# -*- mode: sh -*- # -*- mode: sh -*-
# © Copyright IBM Corporation 2015, 2022 # © Copyright IBM Corporation 2015, 2023
# #
# #
# Licensed under the Apache License, Version 2.0 (the "License"); # Licensed under the Apache License, Version 2.0 (the "License");
@@ -42,21 +42,12 @@ if ($UBUNTU); then
echo "deb ${APT_URL} ${UBUNTU_CODENAME}-security main restricted" >> /etc/apt/sources.list echo "deb ${APT_URL} ${UBUNTU_CODENAME}-security main restricted" >> /etc/apt/sources.list
# Install additional packages required by MQ, this install process and the runtime scripts # Install additional packages required by MQ, this install process and the runtime scripts
EXTRA_DEBS="bash bc ca-certificates coreutils curl debianutils file findutils gawk grep libc-bin mount passwd procps sed tar util-linux" EXTRA_DEBS="bash bc ca-certificates coreutils curl debianutils file findutils gawk grep libc-bin mount passwd procps sed tar util-linux"
# On ARM CPUs, there is no IBM JRE, so install another one
if [ "${CPU_ARCH}" == "aarch64" ]; then
EXTRA_DEBS="${EXTRA_DEBS} openjdk-8-jre"
fi
apt-get update apt-get update
apt-get install -y --no-install-recommends ${EXTRA_DEBS} apt-get install -y --no-install-recommends ${EXTRA_DEBS}
fi fi
if ($RPM); then if ($RPM); then
EXTRA_RPMS="bash bc ca-certificates file findutils gawk glibc-common grep ncurses-compat-libs passwd procps-ng sed shadow-utils tar util-linux which" EXTRA_RPMS="bash bc ca-certificates file findutils gawk glibc-common grep ncurses-compat-libs passwd procps-ng sed shadow-utils tar util-linux which"
# On ARM CPUs, there is no IBM JRE, so install another one
if [ "${CPU_ARCH}" == "aarch64" ]; then
EXTRA_RPMS="${EXTRA_RPMS} java-1.8.0-openjdk-headless"
fi
# Install additional packages required by MQ, this install process and the runtime scripts # Install additional packages required by MQ, this install process and the runtime scripts
$YUM && yum -y install --setopt install_weak_deps=false ${EXTRA_RPMS} $YUM && yum -y install --setopt install_weak_deps=false ${EXTRA_RPMS}
$MICRODNF && microdnf --disableplugin=subscription-manager install ${EXTRA_RPMS} $MICRODNF && microdnf --disableplugin=subscription-manager install ${EXTRA_RPMS}

3
renovate.json Normal file
View File

@@ -0,0 +1,3 @@
{
"$schema": "https://docs.renovatebot.com/renovate-schema.json"
}

View File

@@ -0,0 +1,669 @@
/*
© Copyright IBM Corporation 2017, 2023
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
http://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 containerengine
import (
"context"
"encoding/json"
"io"
"os"
"os/exec"
"path/filepath"
"strconv"
"strings"
"time"
)
type ContainerInterface interface {
ContainerCreate(config *ContainerConfig, hostConfig *ContainerHostConfig, networkingConfig *ContainerNetworkSettings, containerName string) (string, error)
ContainerStop(container string, timeout *time.Duration) error
ContainerKill(container string, signal string) error
ContainerRemove(container string, options ContainerRemoveOptions) error
ContainerStart(container string, options ContainerStartOptions) error
ContainerWait(ctx context.Context, container string, condition string) (<-chan int64, <-chan error)
GetContainerLogs(ctx context.Context, container string, options ContainerLogsOptions) (string, error)
CopyFromContainer(container, srcPath string) ([]byte, error)
GetContainerPort(ID string, hostPort int) (string, error)
GetContainerIPAddress(ID string) (string, error)
ContainerInspectWithFormat(format string, ID string) (string, error)
ExecContainer(ID string, user string, cmd []string) (int, string)
GetMQVersion(image string) (string, error)
ContainerInspect(containerID string) (ContainerDetails, error)
NetworkCreate(name string, options NetworkCreateOptions) (string, error)
NetworkRemove(network string) error
VolumeCreate(options VolumeCreateOptions) (string, error)
VolumeRemove(volumeID string, force bool) error
ImageBuild(context io.Reader, tag string, dockerfilename string) (string, error)
ImageRemove(image string, options ImageRemoveOptions) (bool, error)
ImageInspectWithFormat(format string, ID string) (string, error)
}
type ContainerClient struct {
ContainerTool string
Version string
}
// objects
var objVolume = "volume"
var objImage = "image"
var objPort = "port"
var objNetwork = "network"
// verbs
var listContainers = "ps"
var listImages = "images"
var create = "create"
var startContainer = "start"
var waitContainer = "wait"
var execContainer = "exec"
var getLogs = "logs"
var stopContainer = "stop"
var remove = "rm"
var inspect = "inspect"
var copyFile = "cp"
var build = "build"
var killContainer = "kill"
// args
var argEntrypoint = "--entrypoint"
var argUser = "--user"
var argExpose = "--expose"
var argVolume = "--volume"
var argPublish = "--publish"
var argPrivileged = "--privileged"
var argAddCapability = "--cap-add"
var argDropCapability = "--cap-drop"
var argName = "--name"
var argCondition = "--condition"
var argEnvironmentVariable = "--env"
var argTail = "--tail"
var argForce = "--force"
var argVolumes = "--volumes"
var argHostname = "--hostname"
var argDriver = "--driver"
var argFile = "--file"
var argQuiet = "--quiet"
var argTag = "--tag"
var argFormat = "--format"
var argNetwork = "--network"
var argSecurityOptions = "--security-opt"
var argSignal = "--signal"
// generic
var toolVersion = "version"
var ContainerStateNotRunning = "not-running"
var ContainerStateStopped = "stopped"
type ContainerConfig struct {
Image string
Hostname string
User string
Entrypoint []string
Env []string
ExposedPorts []string
}
type ContainerDetails struct {
ID string
Name string
Image string
Path string
Args []string
Config ContainerConfig
HostConfig ContainerHostConfig
}
type ContainerDetailsLogging struct {
ID string
Name string
Image string
Path string
Args []string
CapAdd []string
CapDrop []string
User string
Env []string
}
type ContainerHostConfig struct {
Binds []string // Bindings onto a volume
PortBindings []PortBinding //Bindings from a container port to a port on the host
Privileged bool // Give extended privileges to container
CapAdd []string // Linux capabilities to add to the container
CapDrop []string // Linux capabilities to drop from the container
SecurityOpt []string
}
type ContainerNetworkSettings struct {
Networks []string // A list of networks to connect the container to
}
type ContainerRemoveOptions struct {
Force bool
RemoveVolumes bool
}
type ContainerStartOptions struct {
}
type NetworkCreateOptions struct {
}
type ContainerLogsOptions struct {
}
type ImageRemoveOptions struct {
Force bool
}
type VolumeCreateOptions struct {
Name string
Driver string
}
// Binding from a container port to a port on the host
type PortBinding struct {
HostIP string
HostPort string //Port to map to on the host
ContainerPort string //Exposed port on the container
}
// NewContainerClient returns a new container client
// Defaults to using podman
func NewContainerClient() ContainerClient {
tool, set := os.LookupEnv("COMMAND")
if !set {
tool = "podman"
}
return ContainerClient{
ContainerTool: tool,
Version: GetContainerToolVersion(tool),
}
}
// GetContainerToolVersion returns the version of the container tool being used
func GetContainerToolVersion(containerTool string) string {
if containerTool == "docker" {
args := []string{"version", "--format", "'{{.Client.Version}}'"}
v, err := exec.Command("docker", args...).Output()
if err != nil {
return "0.0.0"
}
return string(v)
} else if containerTool == "podman" {
//Default to checking the version of podman
args := []string{"version", "--format", "'{{.Version}}'"}
v, err := exec.Command("podman", args...).Output()
if err != nil {
return "0.0.0"
}
return string(v)
}
return "0.0.0"
}
// GetMQVersion returns the MQ version of a given container image
func (cli ContainerClient) GetMQVersion(image string) (string, error) {
v, err := cli.ImageInspectWithFormat("{{.Config.Labels.version}}", image)
if err != nil {
return "", err
}
return v, nil
}
// ImageInspectWithFormat inspects an image with a given formatting string
func (cli ContainerClient) ImageInspectWithFormat(format string, ID string) (string, error) {
args := []string{
objImage,
inspect,
ID,
}
if format != "" {
args = append(args, []string{argFormat, format}...)
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return "", err
}
return string(output), nil
}
// ContainerInspectWithFormat inspects a container with a given formatting string
func (cli ContainerClient) ContainerInspectWithFormat(format string, ID string) (string, error) {
args := []string{
inspect,
ID,
}
if format != "" {
args = append(args, []string{argFormat, format}...)
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return "", err
}
return string(output), nil
}
// GetContainerPort gets the ports on a container
func (cli ContainerClient) GetContainerPort(ID string, hostPort int) (string, error) {
args := []string{
objPort,
ID,
strconv.Itoa(hostPort),
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return "", err
}
o := SanitizeString(string(output))
return strings.Split((o), ":")[1], nil
}
// GetContainerIPAddress gets the IP address of a container
func (cli ContainerClient) GetContainerIPAddress(ID string) (string, error) {
v, err := cli.ContainerInspectWithFormat("{{.NetworkSettings.IPAddress}}", ID)
if err != nil {
return "", err
}
return v, nil
}
// CopyFromContainer copies a file from a container and returns its contents
func (cli ContainerClient) CopyFromContainer(container, srcPath string) ([]byte, error) {
tmpDir, err := os.MkdirTemp("", "tmp")
if err != nil {
return nil, err
}
defer os.RemoveAll(tmpDir)
args := []string{
copyFile,
container + ":" + srcPath,
tmpDir + "/.",
}
_, err = exec.Command(cli.ContainerTool, args...).CombinedOutput()
if err != nil {
return nil, err
}
//Get file name
fname := filepath.Base(srcPath)
data, err := os.ReadFile(filepath.Join(tmpDir, fname))
if err != nil {
return nil, err
}
//Remove the file
err = os.Remove(filepath.Join(tmpDir, fname))
if err != nil {
return nil, err
}
return data, nil
}
func (cli ContainerClient) ContainerInspect(containerID string) (ContainerDetails, error) {
args := []string{
inspect,
containerID,
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return ContainerDetails{}, err
}
var container ContainerDetails
err = json.Unmarshal(output, &container)
if err != nil {
return ContainerDetails{}, err
}
return container, err
}
func (cli ContainerClient) ContainerStop(container string, timeout *time.Duration) error {
args := []string{
stopContainer,
container,
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
return err
}
func (cli ContainerClient) ContainerKill(container string, signal string) error {
args := []string{
killContainer,
container,
}
if signal != "" {
args = append(args, []string{argSignal, signal}...)
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
return err
}
func (cli ContainerClient) ContainerRemove(container string, options ContainerRemoveOptions) error {
args := []string{
remove,
container,
}
if options.Force {
args = append(args, argForce)
}
if options.RemoveVolumes {
args = append(args, argVolumes)
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
//Silently error as the exit code 125 is present on sucessful deletion
if strings.Contains(err.Error(), "125") {
return nil
}
return err
}
return nil
}
func (cli ContainerClient) ExecContainer(ID string, user string, cmd []string) (int, string) {
args := []string{
execContainer,
}
if user != "" {
args = append(args, []string{argUser, user}...)
}
args = append(args, ID)
args = append(args, cmd...)
ctx := context.Background()
output, err := exec.CommandContext(ctx, cli.ContainerTool, args...).CombinedOutput()
if err != nil {
if err.(*exec.ExitError) != nil {
return err.(*exec.ExitError).ExitCode(), string(output)
} else {
return 9897, string(output)
}
}
return 0, string(output)
}
func (cli ContainerClient) ContainerStart(container string, options ContainerStartOptions) error {
args := []string{
startContainer,
container,
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
return err
}
// ContainerWait starts waiting for a container. It returns an int64 channel for receiving an exit code and an error channel for receiving errors.
// The channels returned from this function should be used to receive the results from the wait command.
func (cli ContainerClient) ContainerWait(ctx context.Context, container string, condition string) (<-chan int64, <-chan error) {
args := []string{
waitContainer,
container,
}
if cli.ContainerTool == "podman" {
if condition == ContainerStateNotRunning {
condition = ContainerStateStopped
}
args = append(args, []string{argCondition, string(condition)}...)
}
resultC := make(chan int64)
errC := make(chan error, 1)
output, err := exec.CommandContext(ctx, cli.ContainerTool, args...).Output()
if err != nil {
errC <- err
return resultC, errC
}
go func() {
out := strings.TrimSuffix(string(output), "\n")
exitCode, err := strconv.Atoi(out)
if err != nil {
errC <- err
return
}
resultC <- int64(exitCode)
}()
return resultC, errC
}
func (cli ContainerClient) GetContainerLogs(ctx context.Context, container string, options ContainerLogsOptions) (string, error) {
args := []string{
getLogs,
container,
}
output, err := exec.Command(cli.ContainerTool, args...).CombinedOutput()
if err != nil {
return "", err
}
return string(output), nil
}
func (cli ContainerClient) NetworkCreate(name string, options NetworkCreateOptions) (string, error) {
args := []string{
objNetwork,
create,
}
netID, err := exec.Command(cli.ContainerTool, args...).CombinedOutput()
if err != nil {
return "", err
}
networkID := SanitizeString(string(netID))
return networkID, nil
}
func (cli ContainerClient) NetworkRemove(network string) error {
args := []string{
objNetwork,
remove,
}
_, err := exec.Command(cli.ContainerTool, args...).CombinedOutput()
return err
}
func (cli ContainerClient) VolumeCreate(options VolumeCreateOptions) (string, error) {
args := []string{
objVolume,
create,
options.Name,
}
if options.Driver != "" {
args = append(args, []string{argDriver, options.Driver}...)
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return "", err
}
name := SanitizeString(string(output))
return name, nil
}
func (cli ContainerClient) VolumeRemove(volumeID string, force bool) error {
args := []string{
objVolume,
remove,
volumeID,
}
if force {
args = append(args, argForce)
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
return err
}
func (cli ContainerClient) ImageBuild(context io.Reader, tag string, dockerfilename string) (string, error) {
args := []string{
objImage,
build,
}
//dockerfilename includes the path to the dockerfile
//When using podman use the full path including the name of the Dockerfile
if cli.ContainerTool == "podman" {
args = append(args, []string{argFile, dockerfilename}...)
}
if tag != "" {
args = append(args, []string{argTag, tag}...)
}
args = append(args, argQuiet)
//When using docker remove the name 'DockerFile' from the string
if cli.ContainerTool == "docker" {
dfn := strings.ReplaceAll(dockerfilename, "Dockerfile", "")
args = append(args, dfn)
}
output, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return "", err
}
sha := SanitizeString(string(output))
return sha, nil
}
func (cli ContainerClient) ImageRemove(image string, options ImageRemoveOptions) (bool, error) {
args := []string{
objImage,
remove,
image,
}
if options.Force {
args = append(args, argForce)
}
_, err := exec.Command(cli.ContainerTool, args...).Output()
if err != nil {
return false, err
}
return true, nil
}
func (cli ContainerClient) ContainerCreate(config *ContainerConfig, hostConfig *ContainerHostConfig, networkingConfig *ContainerNetworkSettings, containerName string) (string, error) {
args := []string{
create,
argName,
containerName,
}
args = getHostConfigArgs(args, hostConfig)
args = getNetworkConfigArgs(args, networkingConfig)
args = getContainerConfigArgs(args, config, cli.ContainerTool)
output, err := exec.Command(cli.ContainerTool, args...).Output()
lines := strings.Split(strings.ReplaceAll(string(output), "\r\n", "\n"), "\n")
if err != nil {
return lines[0], err
}
return lines[0], nil
}
// getContainerConfigArgs converts a ContainerConfig into a set of cli arguments
func getContainerConfigArgs(args []string, config *ContainerConfig, toolName string) []string {
argList := []string{}
if config.Entrypoint != nil && toolName == "podman" {
entrypoint := "[\""
for i, commandPart := range config.Entrypoint {
if i != len(config.Entrypoint)-1 {
entrypoint += commandPart + "\",\""
} else {
//terminate list
entrypoint += commandPart + "\"]"
}
}
args = append(args, []string{argEntrypoint, entrypoint}...)
}
if config.Entrypoint != nil && toolName == "docker" {
ep1 := ""
for i, commandPart := range config.Entrypoint {
if i == 0 {
ep1 = commandPart
} else {
argList = append(argList, commandPart)
}
}
args = append(args, []string{argEntrypoint, ep1}...)
}
if config.User != "" {
args = append(args, []string{argUser, config.User}...)
}
if config.ExposedPorts != nil {
for _, port := range config.ExposedPorts {
args = append(args, []string{argExpose, port}...)
}
}
if config.Hostname != "" {
args = append(args, []string{argHostname, config.Hostname}...)
}
for _, env := range config.Env {
args = append(args, []string{argEnvironmentVariable, env}...)
}
if config.Image != "" {
args = append(args, config.Image)
}
if config.Entrypoint != nil && toolName == "docker" {
args = append(args, argList...)
}
return args
}
// getHostConfigArgs converts a ContainerHostConfig into a set of cli arguments
func getHostConfigArgs(args []string, hostConfig *ContainerHostConfig) []string {
if hostConfig.Binds != nil {
for _, volume := range hostConfig.Binds {
args = append(args, []string{argVolume, volume}...)
}
}
if hostConfig.PortBindings != nil {
for _, binding := range hostConfig.PortBindings {
pub := binding.HostIP + ":" + binding.HostPort + ":" + binding.ContainerPort
args = append(args, []string{argPublish, pub}...)
}
}
if hostConfig.Privileged {
args = append(args, []string{argPrivileged}...)
}
if hostConfig.CapAdd != nil {
for _, capability := range hostConfig.CapAdd {
args = append(args, []string{argAddCapability, string(capability)}...)
}
}
if hostConfig.CapDrop != nil {
for _, capability := range hostConfig.CapDrop {
args = append(args, []string{argDropCapability, string(capability)}...)
}
}
if hostConfig.SecurityOpt != nil {
for _, securityOption := range hostConfig.SecurityOpt {
args = append(args, []string{argSecurityOptions, string(securityOption)}...)
}
}
return args
}
// getNetworkConfigArgs converts a set of ContainerNetworkSettings into a set of cli arguments
func getNetworkConfigArgs(args []string, networkingConfig *ContainerNetworkSettings) []string {
if networkingConfig.Networks != nil {
for _, netID := range networkingConfig.Networks {
args = append(args, []string{argNetwork, netID}...)
}
}
return args
}
func SanitizeString(s string) string {
s = strings.Replace(s, " ", "", -1)
s = strings.Replace(s, "\t", "", -1)
s = strings.Replace(s, "\n", "", -1)
return s
}

View File

@@ -2,7 +2,7 @@
// +build mqdev // +build mqdev
/* /*
© Copyright IBM Corporation 2018, 2022 © Copyright IBM Corporation 2018, 2023
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.
@@ -19,37 +19,30 @@ limitations under the License.
package main package main
import ( import (
"context" "crypto/tls"
"fmt"
"path/filepath" "path/filepath"
"strings" "strings"
"testing" "testing"
"time" "time"
"crypto/tls"
"github.com/docker/docker/api/types/container" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
"github.com/docker/docker/api/types/network"
"github.com/docker/docker/client"
"github.com/docker/go-connections/nat"
) )
// TestDevGoldenPath tests using the default values for the default developer config. // TestDevGoldenPath tests using the default values for the default developer config.
// Note: This test requires a separate container image to be available for the JMS tests. // Note: This test requires a separate container image to be available for the JMS tests.
func TestDevGoldenPath(t *testing.T) { func TestDevGoldenPath(t *testing.T) {
t.Parallel() t.Parallel()
cli := ce.NewContainerClient()
cli, err := client.NewClientWithOpts(client.FromEnv)
if err != nil {
t.Fatal(err)
}
qm := "qm1" qm := "qm1"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=" + qm, "MQ_QMGR_NAME=" + qm,
"DEBUG=true", "DEBUG=true",
}, },
} }
id := runContainerWithPorts(t, cli, &containerConfig, []int{9443}) id := runContainerWithPorts(t, cli, &containerConfig, []int{9443, 1414})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
waitForReady(t, cli, id) waitForReady(t, cli, id)
waitForWebReady(t, cli, id, insecureTLSConfig) waitForWebReady(t, cli, id, insecureTLSConfig)
@@ -74,15 +67,12 @@ func TestDevGoldenPath(t *testing.T) {
func TestDevSecure(t *testing.T) { func TestDevSecure(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
const tlsPassPhrase string = "passw0rd" const tlsPassPhrase string = "passw0rd"
qm := "qm1" qm := "qm1"
appPassword := "differentPassw0rd" appPassword := "differentPassw0rd"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=" + qm, "MQ_QMGR_NAME=" + qm,
@@ -93,67 +83,67 @@ func TestDevSecure(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
}, },
}
// Assign a random port for the web server on the host // Assign a random port for the web server on the host
// TODO: Don't do this for all tests // TODO: Don't do this for all tests
PortBindings: nat.PortMap{ var binding ce.PortBinding
"9443/tcp": []nat.PortBinding{ ports := []int{9443, 1414}
{ for _, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0", HostIP: "0.0.0.0",
},
},
},
} }
networkingConfig := network.NetworkingConfig{} hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) }
networkingConfig := ce.ContainerNetworkSettings{}
ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
cert := filepath.Join(tlsDir(t, true), "server.crt") cert := filepath.Join(tlsDir(t, true), "server.crt")
waitForWebReady(t, cli, ctr.ID, createTLSConfig(t, cert, tlsPassPhrase)) waitForWebReady(t, cli, ID, createTLSConfig(t, cert, tlsPassPhrase))
t.Run("JMS", func(t *testing.T) { t.Run("JMS", func(t *testing.T) {
// OpenJDK is used for running tests, hence pass "false" for 7th parameter. // OpenJDK is used for running tests, hence pass "false" for 7th parameter.
// Cipher name specified is compliant with non-IBM JRE naming. // Cipher name specified is compliant with non-IBM JRE naming.
runJMSTests(t, cli, ctr.ID, true, "app", appPassword, "false", "TLS_RSA_WITH_AES_256_CBC_SHA256") runJMSTests(t, cli, ID, true, "app", appPassword, "false", "TLS_RSA_WITH_AES_256_CBC_SHA256")
}) })
t.Run("REST admin", func(t *testing.T) { t.Run("REST admin", func(t *testing.T) {
testRESTAdmin(t, cli, ctr.ID, insecureTLSConfig, "") testRESTAdmin(t, cli, ID, insecureTLSConfig, "")
}) })
t.Run("REST messaging", func(t *testing.T) { t.Run("REST messaging", func(t *testing.T) {
testRESTMessaging(t, cli, ctr.ID, insecureTLSConfig, qm, "app", appPassword, "") testRESTMessaging(t, cli, ID, insecureTLSConfig, qm, "app", appPassword, "")
}) })
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
func TestDevWebDisabled(t *testing.T) { func TestDevWebDisabled(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil { containerConfig := ce.ContainerConfig{
t.Fatal(err)
}
containerConfig := container.Config{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=qm1", "MQ_QMGR_NAME=qm1",
"MQ_ENABLE_EMBEDDED_WEB_SERVER=false", "MQ_ENABLE_EMBEDDED_WEB_SERVER=false",
}, },
} }
id := runContainer(t, cli, &containerConfig) id := runContainerWithPorts(t, cli, &containerConfig, []int{1414})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
waitForReady(t, cli, id) waitForReady(t, cli, id)
t.Run("Web", func(t *testing.T) { t.Run("Web", func(t *testing.T) {
_, dspmqweb := execContainer(t, cli, id, "", []string{"dspmqweb"}) _, dspmqweb := cli.ExecContainer(id, "", []string{"dspmqweb"})
if !strings.Contains(dspmqweb, "Server mqweb is not running.") && !strings.Contains(dspmqweb, "MQWB1125I") { if !strings.Contains(dspmqweb, "Server mqweb is not running.") && !strings.Contains(dspmqweb, "MQWB1125I") {
t.Errorf("Expected dspmqweb to say 'Server is not running' or 'MQWB1125I'; got \"%v\"", dspmqweb) t.Errorf("Expected dspmqweb to say 'Server is not running' or 'MQWB1125I'; got \"%v\"", dspmqweb)
} }
@@ -171,11 +161,8 @@ func TestDevWebDisabled(t *testing.T) {
func TestDevConfigDisabled(t *testing.T) { func TestDevConfigDisabled(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil { containerConfig := ce.ContainerConfig{
t.Fatal(err)
}
containerConfig := container.Config{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=qm1", "MQ_QMGR_NAME=qm1",
@@ -199,11 +186,8 @@ func TestDevConfigDisabled(t *testing.T) {
func TestSSLKEYRBlank(t *testing.T) { func TestSSLKEYRBlank(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil { containerConfig := ce.ContainerConfig{
t.Fatal(err)
}
containerConfig := container.Config{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -246,12 +230,9 @@ func TestSSLKEYRBlank(t *testing.T) {
func TestSSLKEYRWithSuppliedKeyAndCert(t *testing.T) { func TestSSLKEYRWithSuppliedKeyAndCert(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -259,24 +240,24 @@ func TestSSLKEYRWithSuppliedKeyAndCert(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// execute runmqsc to display qmgr SSLKEYR and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslkeyROutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"}) _, sslkeyROutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"})
if !strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") || !strings.Contains(sslkeyROutput, "CERTLABL(default)") { if !strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") || !strings.Contains(sslkeyROutput, "CERTLABL(default)") {
// Although queue manager is ready, it may be that MQSC scripts have not been applied yet. // Although queue manager is ready, it may be that MQSC scripts have not been applied yet.
// Hence wait for a second and retry few times before giving up. // Hence wait for a second and retry few times before giving up.
@@ -284,33 +265,30 @@ func TestSSLKEYRWithSuppliedKeyAndCert(t *testing.T) {
var i int var i int
for i = 0; i < waitCount; i++ { for i = 0; i < waitCount; i++ {
time.Sleep(1 * time.Second) time.Sleep(1 * time.Second)
_, sslkeyROutput = execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"}) _, sslkeyROutput = execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"})
if strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") && strings.Contains(sslkeyROutput, "CERTLABL(default)") { if strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") && strings.Contains(sslkeyROutput, "CERTLABL(default)") {
break break
} }
} }
// Failed to get expected output? dump the contents of mqsc files. // Failed to get expected output? dump the contents of mqsc files.
if i == waitCount { if i == waitCount {
_, tls15mqsc := execContainer(t, cli, ctr.ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"}) _, tls15mqsc := execContainer(t, cli, ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"})
_, autoMQSC := execContainer(t, cli, ctr.ID, "", []string{"cat", "/mnt/mqm/data/qmgrs/QM1/autocfg/cached.mqsc"}) _, autoMQSC := execContainer(t, cli, ID, "", []string{"cat", "/mnt/mqm/data/qmgrs/QM1/autocfg/cached.mqsc"})
t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\" \n AutoConfig MQSC file contents %v\n 15-tls: %v", sslkeyROutput, autoMQSC, tls15mqsc) t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\" \n AutoConfig MQSC file contents %v\n 15-tls: %v", sslkeyROutput, autoMQSC, tls15mqsc)
} }
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Test with CA cert // Test with CA cert
func TestSSLKEYRWithCACert(t *testing.T) { func TestSSLKEYRWithCACert(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -318,32 +296,35 @@ func TestSSLKEYRWithCACert(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDirWithCA(t, false) + ":/etc/mqm/pki/keys/QM1CA", tlsDirWithCA(t, false) + ":/etc/mqm/pki/keys/QM1CA",
}, },
// Assign a random port for the web server on the host
PortBindings: nat.PortMap{
"9443/tcp": []nat.PortBinding{
{
HostIP: "0.0.0.0",
},
},
},
} }
networkingConfig := network.NetworkingConfig{} // Assign a random port for the web server on the host
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) var binding ce.PortBinding
ports := []int{9443}
for _, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0",
}
hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
}
networkingConfig := ce.ContainerNetworkSettings{}
ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// execute runmqsc to display qmgr SSLKEYR and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslkeyROutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"}) _, sslkeyROutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"})
if !strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") { if !strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") {
// Although queue manager is ready, it may be that MQSC scripts have not been applied yet. // Although queue manager is ready, it may be that MQSC scripts have not been applied yet.
@@ -352,38 +333,35 @@ func TestSSLKEYRWithCACert(t *testing.T) {
var i int var i int
for i = 0; i < waitCount; i++ { for i = 0; i < waitCount; i++ {
time.Sleep(1 * time.Second) time.Sleep(1 * time.Second)
_, sslkeyROutput = execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"}) _, sslkeyROutput = execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL' | runmqsc"})
if strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") { if strings.Contains(sslkeyROutput, "SSLKEYR(/run/runmqserver/tls/key)") {
break break
} }
} }
// Failed to get expected output? dump the contents of mqsc files. // Failed to get expected output? dump the contents of mqsc files.
if i == waitCount { if i == waitCount {
_, tls15mqsc := execContainer(t, cli, ctr.ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"}) _, tls15mqsc := execContainer(t, cli, ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"})
_, autoMQSC := execContainer(t, cli, ctr.ID, "", []string{"cat", "/mnt/mqm/data/qmgrs/QM1/autocfg/cached.mqsc"}) _, autoMQSC := execContainer(t, cli, ID, "", []string{"cat", "/mnt/mqm/data/qmgrs/QM1/autocfg/cached.mqsc"})
t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"\n AutoConfig MQSC file contents %v\n 15-tls: %v", sslkeyROutput, autoMQSC, tls15mqsc) t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"\n AutoConfig MQSC file contents %v\n 15-tls: %v", sslkeyROutput, autoMQSC, tls15mqsc)
} }
} }
if !strings.Contains(sslkeyROutput, "CERTLABL(QM1CA)") { if !strings.Contains(sslkeyROutput, "CERTLABL(QM1CA)") {
_, autoMQSC := execContainer(t, cli, ctr.ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"}) _, autoMQSC := execContainer(t, cli, ID, "", []string{"cat", "/etc/mqm/15-tls.mqsc"})
t.Errorf("Expected CERTLABL to be 'QM1CA' but it is not; got \"%v\" \n MQSC File contents %v", sslkeyROutput, autoMQSC) t.Errorf("Expected CERTLABL to be 'QM1CA' but it is not; got \"%v\" \n MQSC File contents %v", sslkeyROutput, autoMQSC)
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Verifies SSLFIPS is set to NO if MQ_ENABLE_FIPS=false // Verifies SSLFIPS is set to NO if MQ_ENABLE_FIPS=false
func TestSSLFIPSNO(t *testing.T) { func TestSSLFIPSNO(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -392,24 +370,24 @@ func TestSSLFIPSNO(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslFIPSOutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"}) _, sslFIPSOutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"})
if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") { if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") {
t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput) t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput)
} }
@@ -422,7 +400,7 @@ func TestSSLFIPSNO(t *testing.T) {
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Verifies SSLFIPS is set to YES if certificates for queue manager // Verifies SSLFIPS is set to YES if certificates for queue manager
@@ -430,13 +408,10 @@ func TestSSLFIPSNO(t *testing.T) {
func TestSSLFIPSYES(t *testing.T) { func TestSSLFIPSYES(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
appPassword := "differentPassw0rd" appPassword := "differentPassw0rd"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_APP_PASSWORD=" + appPassword, "MQ_APP_PASSWORD=" + appPassword,
@@ -446,30 +421,40 @@ func TestSSLFIPSYES(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
}, },
} }
networkingConfig := network.NetworkingConfig{} var binding ce.PortBinding
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ports := []int{1414}
for _, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0",
}
hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
}
networkingConfig := ce.ContainerNetworkSettings{}
ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// Check for expected message on container log // Check for expected message on container log
logs := inspectLogs(t, cli, ctr.ID) logs := inspectLogs(t, cli, ID)
if !strings.Contains(logs, "FIPS cryptography is enabled.") { if !strings.Contains(logs, "FIPS cryptography is enabled.") {
t.Errorf("Expected 'FIPS cryptography is enabled.' but got %v\n", logs) t.Errorf("Expected 'FIPS cryptography is enabled.' but got %v\n", logs)
} }
// execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslFIPSOutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"}) _, sslFIPSOutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"})
if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") { if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") {
t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput) t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput)
} }
@@ -483,26 +468,23 @@ func TestSSLFIPSYES(t *testing.T) {
t.Run("JMS", func(t *testing.T) { t.Run("JMS", func(t *testing.T) {
// Run the JMS tests, with no password specified // Run the JMS tests, with no password specified
runJMSTests(t, cli, ctr.ID, true, "app", appPassword, "false", "TLS_RSA_WITH_AES_256_CBC_SHA256") runJMSTests(t, cli, ID, true, "app", appPassword, "false", "TLS_RSA_WITH_AES_256_CBC_SHA256")
}) })
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// TestDevSecureFIPSYESWeb verifies if the MQ Web Server is running in FIPS mode // TestDevSecureFIPSYESWeb verifies if the MQ Web Server is running in FIPS mode
func TestDevSecureFIPSTrueWeb(t *testing.T) { func TestDevSecureFIPSTrueWeb(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
const tlsPassPhrase string = "passw0rd" const tlsPassPhrase string = "passw0rd"
qm := "qm1" qm := "qm1"
appPassword := "differentPassw0rd" appPassword := "differentPassw0rd"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=" + qm, "MQ_QMGR_NAME=" + qm,
@@ -514,65 +496,65 @@ func TestDevSecureFIPSTrueWeb(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
tlsDir(t, false) + ":/etc/mqm/pki/trust/default", tlsDir(t, false) + ":/etc/mqm/pki/trust/default",
}, },
}
// Assign a random port for the web server on the host // Assign a random port for the web server on the host
// TODO: Don't do this for all tests // TODO: Don't do this for all tests
PortBindings: nat.PortMap{ var binding ce.PortBinding
"9443/tcp": []nat.PortBinding{ ports := []int{9443}
{ for _, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0", HostIP: "0.0.0.0",
},
},
},
} }
networkingConfig := network.NetworkingConfig{} hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) }
networkingConfig := ce.ContainerNetworkSettings{}
ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
cert := filepath.Join(tlsDir(t, true), "server.crt") cert := filepath.Join(tlsDir(t, true), "server.crt")
waitForWebReady(t, cli, ctr.ID, createTLSConfig(t, cert, tlsPassPhrase)) waitForWebReady(t, cli, ID, createTLSConfig(t, cert, tlsPassPhrase))
// Create a TLS Config with a cipher to use when connecting over HTTPS // Create a TLS Config with a cipher to use when connecting over HTTPS
var secureTLSConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_RSA_WITH_AES_256_GCM_SHA384}) var secureTLSConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_RSA_WITH_AES_256_GCM_SHA384})
// Put a message to queue // Put a message to queue
t.Run("REST messaging", func(t *testing.T) { t.Run("REST messaging", func(t *testing.T) {
testRESTMessaging(t, cli, ctr.ID, secureTLSConfig, qm, "app", appPassword, "") testRESTMessaging(t, cli, ID, secureTLSConfig, qm, "app", appPassword, "")
}) })
// Create a TLS Config with a non-FIPS cipher to use when connecting over HTTPS // Create a TLS Config with a non-FIPS cipher to use when connecting over HTTPS
var secureNonFIPSCipherConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA}) var secureNonFIPSCipherConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_ECDHE_ECDSA_WITH_RC4_128_SHA})
// Put a message to queue - the attempt to put message will fail with a EOF return message. // Put a message to queue - the attempt to put message will fail with a EOF return message.
t.Run("REST messaging", func(t *testing.T) { t.Run("REST messaging", func(t *testing.T) {
testRESTMessaging(t, cli, ctr.ID, secureNonFIPSCipherConfig, qm, "app", appPassword, "EOF") testRESTMessaging(t, cli, ID, secureNonFIPSCipherConfig, qm, "app", appPassword, "EOF")
}) })
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// TestDevSecureNOFIPSWeb verifies if the MQ Web Server is not running in FIPS mode // TestDevSecureNOFIPSWeb verifies if the MQ Web Server is not running in FIPS mode
func TestDevSecureFalseFIPSWeb(t *testing.T) { func TestDevSecureFalseFIPSWeb(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
const tlsPassPhrase string = "passw0rd" const tlsPassPhrase string = "passw0rd"
qm := "qm1" qm := "qm1"
appPassword := "differentPassw0rd" appPassword := "differentPassw0rd"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=" + qm, "MQ_QMGR_NAME=" + qm,
@@ -584,38 +566,41 @@ func TestDevSecureFalseFIPSWeb(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
tlsDir(t, false) + ":/etc/mqm/pki/trust/default", tlsDir(t, false) + ":/etc/mqm/pki/trust/default",
}, },
// Assign a random port for the web server on the host
PortBindings: nat.PortMap{
"9443/tcp": []nat.PortBinding{
{
HostIP: "0.0.0.0",
},
},
},
} }
networkingConfig := network.NetworkingConfig{} // Assign a random port for the web server on the host
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) var binding ce.PortBinding
ports := []int{9443}
for _, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0",
}
hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
}
networkingConfig := ce.ContainerNetworkSettings{}
ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
cert := filepath.Join(tlsDir(t, true), "server.crt") cert := filepath.Join(tlsDir(t, true), "server.crt")
waitForWebReady(t, cli, ctr.ID, createTLSConfig(t, cert, tlsPassPhrase)) waitForWebReady(t, cli, ID, createTLSConfig(t, cert, tlsPassPhrase))
// As FIPS is not enabled, the MQ WebServer (actually Java) will choose a JSSE provider from the list // As FIPS is not enabled, the MQ WebServer (actually Java) will choose a JSSE provider from the list
// specified in java.security file. We will need to enable java.net.debug and then parse the web server // specified in java.security file. We will need to enable java.net.debug and then parse the web server
// logs to check what JJSE provider is being used. Hence just check the jvm.options file does not contain // logs to check what JJSE provider is being used. Hence just check the jvm.options file does not contain
// -Dcom.ibm.jsse2.usefipsprovider line. // -Dcom.ibm.jsse2.usefipsprovider line.
_, jvmOptionsOutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "cat /var/mqm/web/installations/Installation1/servers/mqweb/configDropins/defaults/jvm.options"}) _, jvmOptionsOutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "cat /var/mqm/web/installations/Installation1/servers/mqweb/configDropins/defaults/jvm.options"})
if strings.Contains(jvmOptionsOutput, "-Dcom.ibm.jsse2.usefipsprovider") { if strings.Contains(jvmOptionsOutput, "-Dcom.ibm.jsse2.usefipsprovider") {
t.Errorf("Did not expect -Dcom.ibm.jsse2.usefipsprovider but it is not; got \"%v\"", jvmOptionsOutput) t.Errorf("Did not expect -Dcom.ibm.jsse2.usefipsprovider but it is not; got \"%v\"", jvmOptionsOutput)
} }
@@ -623,24 +608,21 @@ func TestDevSecureFalseFIPSWeb(t *testing.T) {
// Just do a HTTPS GET as well to query installation details. // Just do a HTTPS GET as well to query installation details.
var secureTLSConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_RSA_WITH_AES_256_GCM_SHA384}) var secureTLSConfig *tls.Config = createTLSConfigWithCipher(t, cert, tlsPassPhrase, []uint16{tls.TLS_RSA_WITH_AES_256_GCM_SHA384})
t.Run("REST admin", func(t *testing.T) { t.Run("REST admin", func(t *testing.T) {
testRESTAdmin(t, cli, ctr.ID, secureTLSConfig, "") testRESTAdmin(t, cli, ID, secureTLSConfig, "")
}) })
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Verify SSLFIPS is set to NO if no certificates were supplied // Verify SSLFIPS is set to NO if no certificates were supplied
func TestSSLFIPSTrueNoCerts(t *testing.T) { func TestSSLFIPSTrueNoCerts(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
appPassword := "differentPassw0rd" appPassword := "differentPassw0rd"
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_APP_PASSWORD=" + appPassword, "MQ_APP_PASSWORD=" + appPassword,
@@ -650,23 +632,23 @@ func TestSSLFIPSTrueNoCerts(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslFIPSOutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"}) _, sslFIPSOutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"})
if !strings.Contains(sslFIPSOutput, "SSLKEYR( )") { if !strings.Contains(sslFIPSOutput, "SSLKEYR( )") {
t.Errorf("Expected SSLKEYR to be ' ' but it is not; got \"%v\"", sslFIPSOutput) t.Errorf("Expected SSLKEYR to be ' ' but it is not; got \"%v\"", sslFIPSOutput)
} }
@@ -679,19 +661,16 @@ func TestSSLFIPSTrueNoCerts(t *testing.T) {
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Verifies SSLFIPS is set to NO if MQ_ENABLE_FIPS=tru (invalid value) // Verifies SSLFIPS is set to NO if MQ_ENABLE_FIPS=tru (invalid value)
func TestSSLFIPSInvalidValue(t *testing.T) { func TestSSLFIPSInvalidValue(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -700,24 +679,24 @@ func TestSSLFIPSInvalidValue(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/etc/mqm/pki/keys/default", tlsDir(t, false) + ":/etc/mqm/pki/keys/default",
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
waitForReady(t, cli, ctr.ID) waitForReady(t, cli, ID)
// execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes. // execute runmqsc to display qmgr SSLKEYR, SSLFIPS and CERTLABL attibutes.
// Search the console output for exepcted values // Search the console output for exepcted values
_, sslFIPSOutput := execContainer(t, cli, ctr.ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"}) _, sslFIPSOutput := execContainer(t, cli, ID, "", []string{"bash", "-c", "echo 'DISPLAY QMGR SSLKEYR CERTLABL SSLFIPS' | runmqsc"})
if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") { if !strings.Contains(sslFIPSOutput, "SSLKEYR(/run/runmqserver/tls/key)") {
t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput) t.Errorf("Expected SSLKEYR to be '/run/runmqserver/tls/key' but it is not; got \"%v\"", sslFIPSOutput)
} }
@@ -731,19 +710,16 @@ func TestSSLFIPSInvalidValue(t *testing.T) {
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }
// Container creation fails when invalid certs are passed and MQ_ENABLE_FIPS set true // Container creation fails when invalid certs are passed and MQ_ENABLE_FIPS set true
func TestSSLFIPSBadCerts(t *testing.T) { func TestSSLFIPSBadCerts(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -752,25 +728,25 @@ func TestSSLFIPSBadCerts(t *testing.T) {
}, },
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDirInvalid(t, false) + ":/etc/mqm/pki/keys/default", tlsDirInvalid(t, false) + ":/etc/mqm/pki/keys/default",
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, ID)
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
rc := waitForContainer(t, cli, ctr.ID, 20*time.Second) rc := waitForContainer(t, cli, ID, 20*time.Second)
// Expect return code 1 if container failed to create. // Expect return code 1 if container failed to create.
if rc == 1 { if rc == 1 {
// Get container logs and search for specific message. // Get container logs and search for specific message.
logs := inspectLogs(t, cli, ctr.ID) logs := inspectLogs(t, cli, ID)
if strings.Contains(logs, "Failed to parse private key") { if strings.Contains(logs, "Failed to parse private key") {
t.Logf("Container creating failed because of invalid certifates") t.Logf("Container creating failed because of invalid certifates")
} }
@@ -780,5 +756,5 @@ func TestSSLFIPSBadCerts(t *testing.T) {
} }
// Stop the container cleanly // Stop the container cleanly
stopContainer(t, cli, ctr.ID) stopContainer(t, cli, ID)
} }

View File

@@ -2,7 +2,7 @@
// +build mqdev // +build mqdev
/* /*
© Copyright IBM Corporation 2018, 2022 © Copyright IBM Corporation 2018, 2023
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.
@@ -34,9 +34,7 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/api/types/container" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
"github.com/docker/docker/api/types/network"
"github.com/docker/docker/client"
) )
const defaultAdminPassword string = "passw0rd" const defaultAdminPassword string = "passw0rd"
@@ -49,7 +47,7 @@ var insecureTLSConfig *tls.Config = &tls.Config{
InsecureSkipVerify: true, InsecureSkipVerify: true,
} }
func waitForWebReady(t *testing.T, cli *client.Client, ID string, tlsConfig *tls.Config) { func waitForWebReady(t *testing.T, cli ce.ContainerInterface, ID string, tlsConfig *tls.Config) {
t.Logf("%s Waiting for web server to be ready", time.Now().Format(time.RFC3339)) t.Logf("%s Waiting for web server to be ready", time.Now().Format(time.RFC3339))
httpClient := http.Client{ httpClient := http.Client{
Timeout: time.Duration(10 * time.Second), Timeout: time.Duration(10 * time.Second),
@@ -57,7 +55,11 @@ func waitForWebReady(t *testing.T, cli *client.Client, ID string, tlsConfig *tls
TLSClientConfig: tlsConfig, TLSClientConfig: tlsConfig,
}, },
} }
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/admin/installation", getPort(t, cli, ID, 9443)) port, err := cli.GetContainerPort(ID, 9443)
if err != nil {
t.Fatal(err)
}
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/admin/installation", port)
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute) ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute)
defer cancel() defer cancel()
@@ -91,11 +93,16 @@ func tlsDirInvalid(t *testing.T, unixPath bool) string {
} }
// runJMSTests runs a container with a JMS client, which connects to the queue manager container with the specified ID // runJMSTests runs a container with a JMS client, which connects to the queue manager container with the specified ID
func runJMSTests(t *testing.T, cli *client.Client, ID string, tls bool, user, password string, ibmjre string, cipherName string) { func runJMSTests(t *testing.T, cli ce.ContainerInterface, ID string, tls bool, user, password string, ibmjre string, cipherName string) {
containerConfig := container.Config{ port, err := cli.GetContainerPort(ID, 1414)
if err != nil {
t.Error(err)
}
containerConfig := ce.ContainerConfig{
// -e MQ_PORT_1414_TCP_ADDR=9.145.14.173 -e MQ_USERNAME=app -e MQ_PASSWORD=passw0rd -e MQ_CHANNEL=DEV.APP.SVRCONN -e MQ_TLS_TRUSTSTORE=/tls/test.p12 -e MQ_TLS_PASSPHRASE=passw0rd -v /Users/arthurbarr/go/src/github.com/ibm-messaging/mq-container/test/tls:/tls msgtest // -e MQ_PORT_1414_TCP_ADDR=9.145.14.173 -e MQ_USERNAME=app -e MQ_PASSWORD=passw0rd -e MQ_CHANNEL=DEV.APP.SVRCONN -e MQ_TLS_TRUSTSTORE=/tls/test.p12 -e MQ_TLS_PASSPHRASE=passw0rd -v /Users/arthurbarr/go/src/github.com/ibm-messaging/mq-container/test/tls:/tls msgtest
Env: []string{ Env: []string{
"MQ_PORT_1414_TCP_ADDR=" + getIPAddress(t, cli, ID), "MQ_PORT_1414_TCP_ADDR=127.0.0.1",
"MQ_PORT_1414_OVERRIDE=" + port,
"MQ_USERNAME=" + user, "MQ_USERNAME=" + user,
"MQ_CHANNEL=DEV.APP.SVRCONN", "MQ_CHANNEL=DEV.APP.SVRCONN",
"IBMJRE=" + ibmjre, "IBMJRE=" + ibmjre,
@@ -114,26 +121,28 @@ func runJMSTests(t *testing.T, cli *client.Client, ID string, tls bool, user, pa
"MQ_TLS_CIPHER=" + cipherName, "MQ_TLS_CIPHER=" + cipherName,
}...) }...)
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
tlsDir(t, false) + ":/var/tls", tlsDir(t, false) + ":/var/tls",
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, strings.Replace(t.Name()+"JMS", "/", "", -1)) Networks: []string{"host"},
}
jmsID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, strings.Replace(t.Name()+"JMS", "/", "", -1))
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
startContainer(t, cli, ctr.ID) startContainer(t, cli, jmsID)
rc := waitForContainer(t, cli, ctr.ID, 2*time.Minute) rc := waitForContainer(t, cli, jmsID, 2*time.Minute)
if rc != 0 { if rc != 0 {
t.Errorf("JUnit container failed with rc=%v", rc) t.Errorf("JUnit container failed with rc=%v", rc)
} }
// Get console output of the container and process the lines // Get console output of the container and process the lines
// to see if we have any failures // to see if we have any failures
scanner := bufio.NewScanner(strings.NewReader(inspectLogs(t, cli, ctr.ID))) scanner := bufio.NewScanner(strings.NewReader(inspectLogs(t, cli, jmsID)))
for scanner.Scan() { for scanner.Scan() {
s := scanner.Text() s := scanner.Text()
if processJunitLogLine(s) { if processJunitLogLine(s) {
@@ -141,7 +150,7 @@ func runJMSTests(t *testing.T, cli *client.Client, ID string, tls bool, user, pa
} }
} }
defer cleanContainer(t, cli, ctr.ID) defer cleanContainer(t, cli, jmsID)
} }
// Parse JUnit log line and return true if line contains failed or aborted tests // Parse JUnit log line and return true if line contains failed or aborted tests
@@ -205,14 +214,18 @@ func createTLSConfig(t *testing.T, certFile, password string) *tls.Config {
} }
} }
func testRESTAdmin(t *testing.T, cli *client.Client, ID string, tlsConfig *tls.Config, errorExpected string) { func testRESTAdmin(t *testing.T, cli ce.ContainerInterface, ID string, tlsConfig *tls.Config, errorExpected string) {
httpClient := http.Client{ httpClient := http.Client{
Timeout: time.Duration(30 * time.Second), Timeout: time.Duration(30 * time.Second),
Transport: &http.Transport{ Transport: &http.Transport{
TLSClientConfig: tlsConfig, TLSClientConfig: tlsConfig,
}, },
} }
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/admin/installation", getPort(t, cli, ID, 9443)) port, err := cli.GetContainerPort(ID, 9443)
if err != nil {
t.Fatal(err)
}
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/admin/installation", port)
req, err := http.NewRequest("GET", url, nil) req, err := http.NewRequest("GET", url, nil)
req.SetBasicAuth("admin", defaultAdminPassword) req.SetBasicAuth("admin", defaultAdminPassword)
resp, err := httpClient.Do(req) resp, err := httpClient.Do(req)
@@ -248,7 +261,7 @@ func logHTTPResponse(t *testing.T, resp *http.Response) {
t.Logf("HTTP response: %v", string(d)) t.Logf("HTTP response: %v", string(d))
} }
func testRESTMessaging(t *testing.T, cli *client.Client, ID string, tlsConfig *tls.Config, qmName string, user string, password string, errorExpected string) { func testRESTMessaging(t *testing.T, cli ce.ContainerInterface, ID string, tlsConfig *tls.Config, qmName string, user string, password string, errorExpected string) {
httpClient := http.Client{ httpClient := http.Client{
Timeout: time.Duration(30 * time.Second), Timeout: time.Duration(30 * time.Second),
Transport: &http.Transport{ Transport: &http.Transport{
@@ -256,7 +269,11 @@ func testRESTMessaging(t *testing.T, cli *client.Client, ID string, tlsConfig *t
}, },
} }
q := "DEV.QUEUE.1" q := "DEV.QUEUE.1"
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/messaging/qmgr/%s/queue/%s/message", getPort(t, cli, ID, 9443), qmName, q) port, err := cli.GetContainerPort(ID, 9443)
if err != nil {
t.Fatal(err)
}
url := fmt.Sprintf("https://localhost:%s/ibmmq/rest/v1/messaging/qmgr/%s/queue/%s/message", port, qmName, q)
putMessage := []byte("Hello") putMessage := []byte("Hello")
req, err := http.NewRequest("POST", url, bytes.NewBuffer(putMessage)) req, err := http.NewRequest("POST", url, bytes.NewBuffer(putMessage))
req.SetBasicAuth(user, password) req.SetBasicAuth(user, password)

View File

@@ -34,28 +34,9 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/api/types" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
"github.com/docker/docker/api/types/container"
"github.com/docker/docker/api/types/network"
"github.com/docker/docker/api/types/volume"
"github.com/docker/docker/client"
"github.com/docker/docker/pkg/jsonmessage"
"github.com/docker/docker/pkg/stdcopy"
"github.com/docker/go-connections/nat"
) )
type containerDetails struct {
ID string
Name string
Image string
Path string
Args []string
CapAdd []string
CapDrop []string
User string
Env []string
}
func imageName() string { func imageName() string {
image, ok := os.LookupEnv("TEST_IMAGE") image, ok := os.LookupEnv("TEST_IMAGE")
if !ok { if !ok {
@@ -73,7 +54,7 @@ func imageNameDevJMS() string {
} }
// baseImage returns the ID of the underlying base image (e.g. "ubuntu" or "rhel") // baseImage returns the ID of the underlying base image (e.g. "ubuntu" or "rhel")
func baseImage(t *testing.T, cli *client.Client) string { func baseImage(t *testing.T, cli ce.ContainerInterface) string {
rc, out := runContainerOneShot(t, cli, "grep", "^ID=", "/etc/os-release") rc, out := runContainerOneShot(t, cli, "grep", "^ID=", "/etc/os-release")
if rc != 0 { if rc != 0 {
t.Fatal("Couldn't determine base image") t.Fatal("Couldn't determine base image")
@@ -87,7 +68,7 @@ func baseImage(t *testing.T, cli *client.Client) string {
// devImage returns true if the image under test is a developer image, // devImage returns true if the image under test is a developer image,
// determined by use of the MQ_ADMIN_PASSWORD environment variable // determined by use of the MQ_ADMIN_PASSWORD environment variable
func devImage(t *testing.T, cli *client.Client) bool { func devImage(t *testing.T, cli ce.ContainerInterface) bool {
rc, _ := runContainerOneShot(t, cli, "printenv", "MQ_ADMIN_PASSWORD") rc, _ := runContainerOneShot(t, cli, "printenv", "MQ_ADMIN_PASSWORD")
if rc == 0 { if rc == 0 {
return true return true
@@ -107,6 +88,11 @@ func isWSL(t *testing.T) bool {
return false return false
} }
// isARM returns whether we are running an arm64 MacOS machine
func isARM(t *testing.T) bool {
return runtime.GOARCH == "arm64"
}
// getCwd returns the working directory, in an os-specific or UNIX form // getCwd returns the working directory, in an os-specific or UNIX form
func getCwd(t *testing.T, unixPath bool) string { func getCwd(t *testing.T, unixPath bool) string {
dir, err := os.Getwd() dir, err := os.Getwd()
@@ -161,29 +147,17 @@ func getTempDir(t *testing.T, unixStylePath bool) string {
} }
// terminationMessage return the termination message, or an empty string if not set // terminationMessage return the termination message, or an empty string if not set
func terminationMessage(t *testing.T, cli *client.Client, ID string) string { func terminationMessage(t *testing.T, cli ce.ContainerInterface, ID string) string {
r, _, err := cli.CopyFromContainer(context.Background(), ID, "/run/termination-log") r, err := cli.CopyFromContainer(ID, "/run/termination-log")
if err != nil { if err != nil {
t.Log(err) t.Log(err)
t.Log(string(r))
return "" return ""
} }
b, err := ioutil.ReadAll(r) return string(r)
tr := tar.NewReader(bytes.NewReader(b))
_, err = tr.Next()
if err != nil {
t.Log(err)
return ""
}
// read the complete content of the file h.Name into the bs []byte
content, err := ioutil.ReadAll(tr)
if err != nil {
t.Log(err)
return ""
}
return string(content)
} }
func expectTerminationMessage(t *testing.T, cli *client.Client, ID string) { func expectTerminationMessage(t *testing.T, cli ce.ContainerInterface, ID string) {
m := terminationMessage(t, cli, ID) m := terminationMessage(t, cli, ID)
if m == "" { if m == "" {
t.Error("Expected termination message to be set") t.Error("Expected termination message to be set")
@@ -191,10 +165,10 @@ func expectTerminationMessage(t *testing.T, cli *client.Client, ID string) {
} }
// logContainerDetails logs selected details about the container // logContainerDetails logs selected details about the container
func logContainerDetails(t *testing.T, cli *client.Client, ID string) { func logContainerDetails(t *testing.T, cli ce.ContainerInterface, ID string) {
i, err := cli.ContainerInspect(context.Background(), ID) i, err := cli.ContainerInspect(ID)
if err == nil { if err == nil {
d := containerDetails{ d := ce.ContainerDetailsLogging{
ID: ID, ID: ID,
Name: i.Name, Name: i.Name,
Image: i.Image, Image: i.Image,
@@ -210,29 +184,29 @@ func logContainerDetails(t *testing.T, cli *client.Client, ID string) {
} }
} }
func cleanContainerQuiet(t *testing.T, cli *client.Client, ID string) { func cleanContainerQuiet(t *testing.T, cli ce.ContainerInterface, ID string) {
timeout := 10 * time.Second timeout := 10 * time.Second
err := cli.ContainerStop(context.Background(), ID, &timeout) err := cli.ContainerStop(ID, &timeout)
if err != nil { if err != nil {
// Just log the error and continue // Just log the error and continue
t.Log(err) t.Log(err)
} }
opts := types.ContainerRemoveOptions{ opts := ce.ContainerRemoveOptions{
RemoveVolumes: true, RemoveVolumes: true,
Force: true, Force: true,
} }
err = cli.ContainerRemove(context.Background(), ID, opts) err = cli.ContainerRemove(ID, opts)
if err != nil { if err != nil {
t.Error(err) t.Error(err)
} }
} }
func cleanContainer(t *testing.T, cli *client.Client, ID string) { func cleanContainer(t *testing.T, cli ce.ContainerInterface, ID string) {
logContainerDetails(t, cli, ID) logContainerDetails(t, cli, ID)
t.Logf("Stopping container: %v", ID) t.Logf("Stopping container: %v", ID)
timeout := 10 * time.Second timeout := 10 * time.Second
// Stop the container. This allows the coverage output to be generated. // Stop the container. This allows the coverage output to be generated.
err := cli.ContainerStop(context.Background(), ID, &timeout) err := cli.ContainerStop(ID, &timeout)
if err != nil { if err != nil {
// Just log the error and continue // Just log the error and continue
t.Log(err) t.Log(err)
@@ -250,11 +224,11 @@ func cleanContainer(t *testing.T, cli *client.Client, ID string) {
} }
t.Logf("Removing container: %s", ID) t.Logf("Removing container: %s", ID)
opts := types.ContainerRemoveOptions{ opts := ce.ContainerRemoveOptions{
RemoveVolumes: true, RemoveVolumes: true,
Force: true, Force: true,
} }
err = cli.ContainerRemove(context.Background(), ID, opts) err = cli.ContainerRemove(ID, opts)
if err != nil { if err != nil {
t.Error(err) t.Error(err)
} }
@@ -268,17 +242,17 @@ func generateRandomUID() string {
} }
// getDefaultHostConfig creates a HostConfig and populates it with the defaults used in testing // getDefaultHostConfig creates a HostConfig and populates it with the defaults used in testing
func getDefaultHostConfig(t *testing.T, cli *client.Client) *container.HostConfig { func getDefaultHostConfig(t *testing.T, cli ce.ContainerInterface) *ce.ContainerHostConfig {
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ PortBindings: []ce.PortBinding{},
coverageBind(t),
},
PortBindings: nat.PortMap{},
CapDrop: []string{ CapDrop: []string{
"ALL", "ALL",
}, },
Privileged: false, Privileged: false,
} }
if coverage() {
hostConfig.Binds = append(hostConfig.Binds, coverageBind(t))
}
if devImage(t, cli) { if devImage(t, cli) {
// Only needed for a RHEL-based image // Only needed for a RHEL-based image
if baseImage(t, cli) != "ubuntu" { if baseImage(t, cli) != "ubuntu" {
@@ -292,7 +266,7 @@ func getDefaultHostConfig(t *testing.T, cli *client.Client) *container.HostConfi
// runContainerWithHostConfig creates and starts a container, using the supplied HostConfig. // runContainerWithHostConfig creates and starts a container, using the supplied HostConfig.
// Note that a default HostConfig can be created using getDefaultHostConfig. // Note that a default HostConfig can be created using getDefaultHostConfig.
func runContainerWithHostConfig(t *testing.T, cli *client.Client, containerConfig *container.Config, hostConfig *container.HostConfig) string { func runContainerWithHostConfig(t *testing.T, cli ce.ContainerInterface, containerConfig *ce.ContainerConfig, hostConfig *ce.ContainerHostConfig) string {
if containerConfig.Image == "" { if containerConfig.Image == "" {
containerConfig.Image = imageName() containerConfig.Image = imageName()
} }
@@ -300,22 +274,23 @@ func runContainerWithHostConfig(t *testing.T, cli *client.Client, containerConfi
if containerConfig.User == "" { if containerConfig.User == "" {
containerConfig.User = generateRandomUID() containerConfig.User = generateRandomUID()
} }
// if coverage if coverage() {
containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov") containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov")
containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t)) containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t))
networkingConfig := network.NetworkingConfig{} }
networkingConfig := ce.ContainerNetworkSettings{}
t.Logf("Running container (%s)", containerConfig.Image) t.Logf("Running container (%s)", containerConfig.Image)
ctr, err := cli.ContainerCreate(context.Background(), containerConfig, hostConfig, &networkingConfig, t.Name()) ID, err := cli.ContainerCreate(containerConfig, hostConfig, &networkingConfig, t.Name())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
return ctr.ID return ID
} }
// runContainerWithAllConfig creates and starts a container, using the supplied ContainerConfig, HostConfig, // runContainerWithAllConfig creates and starts a container, using the supplied ContainerConfig, HostConfig,
// NetworkingConfig, and container name (or the value of t.Name if containerName=""). // NetworkingConfig, and container name (or the value of t.Name if containerName="").
func runContainerWithAllConfig(t *testing.T, cli *client.Client, containerConfig *container.Config, hostConfig *container.HostConfig, networkingConfig *network.NetworkingConfig, containerName string) string { func runContainerWithAllConfig(t *testing.T, cli ce.ContainerInterface, containerConfig *ce.ContainerConfig, hostConfig *ce.ContainerHostConfig, networkingConfig *ce.ContainerNetworkSettings, containerName string) string {
if containerName == "" { if containerName == "" {
containerName = t.Name() containerName = t.Name()
} }
@@ -326,30 +301,32 @@ func runContainerWithAllConfig(t *testing.T, cli *client.Client, containerConfig
if containerConfig.User == "" { if containerConfig.User == "" {
containerConfig.User = generateRandomUID() containerConfig.User = generateRandomUID()
} }
// if coverage if coverage() {
containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov") containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov")
containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t)) containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t))
}
t.Logf("Running container (%s)", containerConfig.Image) t.Logf("Running container (%s)", containerConfig.Image)
ctr, err := cli.ContainerCreate(context.Background(), containerConfig, hostConfig, networkingConfig, containerName) ID, err := cli.ContainerCreate(containerConfig, hostConfig, networkingConfig, containerName)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
startContainer(t, cli, ctr.ID) startContainer(t, cli, ID)
return ctr.ID return ID
} }
// runContainerWithPorts creates and starts a container, exposing the specified ports on the host. // runContainerWithPorts creates and starts a container, exposing the specified ports on the host.
// If no image is specified in the container config, then the image name is retrieved from the TEST_IMAGE // If no image is specified in the container config, then the image name is retrieved from the TEST_IMAGE
// environment variable. // environment variable.
func runContainerWithPorts(t *testing.T, cli *client.Client, containerConfig *container.Config, ports []int) string { func runContainerWithPorts(t *testing.T, cli ce.ContainerInterface, containerConfig *ce.ContainerConfig, ports []int) string {
hostConfig := getDefaultHostConfig(t, cli) hostConfig := getDefaultHostConfig(t, cli)
var binding ce.PortBinding
for _, p := range ports { for _, p := range ports {
port := nat.Port(fmt.Sprintf("%v/tcp", p)) port := fmt.Sprintf("%v/tcp", p)
hostConfig.PortBindings[port] = []nat.PortBinding{ binding = ce.PortBinding{
{ ContainerPort: port,
HostIP: "0.0.0.0", HostIP: "0.0.0.0",
},
} }
hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
} }
return runContainerWithHostConfig(t, cli, containerConfig, hostConfig) return runContainerWithHostConfig(t, cli, containerConfig, hostConfig)
} }
@@ -357,161 +334,160 @@ func runContainerWithPorts(t *testing.T, cli *client.Client, containerConfig *co
// runContainer creates and starts a container. If no image is specified in // runContainer creates and starts a container. If no image is specified in
// the container config, then the image name is retrieved from the TEST_IMAGE // the container config, then the image name is retrieved from the TEST_IMAGE
// environment variable. // environment variable.
func runContainer(t *testing.T, cli *client.Client, containerConfig *container.Config) string { func runContainer(t *testing.T, cli ce.ContainerInterface, containerConfig *ce.ContainerConfig) string {
return runContainerWithPorts(t, cli, containerConfig, nil) return runContainerWithPorts(t, cli, containerConfig, nil)
} }
// runContainerOneShot runs a container with a custom entrypoint, as the root // runContainerOneShot runs a container with a custom entrypoint, as the root
// user and with default capabilities // user and with default capabilities
func runContainerOneShot(t *testing.T, cli *client.Client, command ...string) (int64, string) { func runContainerOneShot(t *testing.T, cli ce.ContainerInterface, command ...string) (int64, string) {
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Entrypoint: command, Entrypoint: command,
User: "root", User: "root",
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{} hostConfig := ce.ContainerHostConfig{}
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
t.Logf("Running one shot container (%s): %v", containerConfig.Image, command) t.Logf("Running one shot container (%s): %v", containerConfig.Image, command)
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()+"OneShot") ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name()+"OneShot")
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
startOptions := types.ContainerStartOptions{} startOptions := ce.ContainerStartOptions{}
err = cli.ContainerStart(context.Background(), ctr.ID, startOptions) err = cli.ContainerStart(ID, startOptions)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainerQuiet(t, cli, ctr.ID) defer cleanContainerQuiet(t, cli, ID)
rc := waitForContainer(t, cli, ctr.ID, 20*time.Second) rc := waitForContainer(t, cli, ID, 20*time.Second)
out := inspectLogs(t, cli, ctr.ID) out := inspectLogs(t, cli, ID)
t.Logf("One shot container finished with rc=%v, output=%v", rc, out) t.Logf("One shot container finished with rc=%v, output=%v", rc, out)
return rc, out return rc, out
} }
// runContainerOneShot runs a container with a custom entrypoint, as the root // runContainerOneShot runs a container with a custom entrypoint, as the root
// user, with default capabilities, and a volume mounted // user, with default capabilities, and a volume mounted
func runContainerOneShotWithVolume(t *testing.T, cli *client.Client, bind string, command ...string) (int64, string) { func runContainerOneShotWithVolume(t *testing.T, cli ce.ContainerInterface, bind string, command ...string) (int64, string) {
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Entrypoint: command, Entrypoint: command,
User: "root", User: "root",
Image: imageName(), Image: imageName(),
} }
hostConfig := container.HostConfig{ hostConfig := ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
bind, bind,
}, },
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
t.Logf("Running one shot container with volume (%s): %v", containerConfig.Image, command) t.Logf("Running one shot container with volume (%s): %v", containerConfig.Image, command)
ctr, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()+"OneShotVolume") ID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name()+"OneShotVolume")
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
startOptions := types.ContainerStartOptions{} startOptions := ce.ContainerStartOptions{}
err = cli.ContainerStart(context.Background(), ctr.ID, startOptions) err = cli.ContainerStart(ID, startOptions)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer cleanContainerQuiet(t, cli, ctr.ID) defer cleanContainerQuiet(t, cli, ID)
rc := waitForContainer(t, cli, ctr.ID, 20*time.Second) rc := waitForContainer(t, cli, ID, 20*time.Second)
out := inspectLogs(t, cli, ctr.ID) out := inspectLogs(t, cli, ID)
t.Logf("One shot container finished with rc=%v, output=%v", rc, out) t.Logf("One shot container finished with rc=%v, output=%v", rc, out)
return rc, out return rc, out
} }
func startMultiVolumeQueueManager(t *testing.T, cli *client.Client, dataVol bool, qmsharedlogs string, qmshareddata string, env []string) (error, string, string) { func startMultiVolumeQueueManager(t *testing.T, cli ce.ContainerInterface, dataVol bool, qmsharedlogs string, qmshareddata string, env []string) (error, string, string) {
id := strconv.FormatInt(time.Now().UnixNano(), 10) id := strconv.FormatInt(time.Now().UnixNano(), 10)
qmdata := createVolume(t, cli, id) volume := createVolume(t, cli, id)
containerConfig := container.Config{ containerConfig := ce.ContainerConfig{
Image: imageName(), Image: imageName(),
Env: env, Env: env,
} }
var hostConfig container.HostConfig var hostConfig ce.ContainerHostConfig
if !dataVol { if !dataVol {
hostConfig = container.HostConfig{} hostConfig = ce.ContainerHostConfig{}
} else if qmsharedlogs == "" && qmshareddata == "" { } else if qmsharedlogs == "" && qmshareddata == "" {
hostConfig = getHostConfig(t, 1, "", "", qmdata.Name) hostConfig = getHostConfig(t, 1, "", "", volume)
} else if qmsharedlogs == "" { } else if qmsharedlogs == "" {
hostConfig = getHostConfig(t, 2, "", qmshareddata, qmdata.Name) hostConfig = getHostConfig(t, 2, "", qmshareddata, volume)
} else if qmshareddata == "" { } else if qmshareddata == "" {
hostConfig = getHostConfig(t, 3, qmsharedlogs, "", qmdata.Name) hostConfig = getHostConfig(t, 3, qmsharedlogs, "", volume)
} else { } else {
hostConfig = getHostConfig(t, 4, qmsharedlogs, qmshareddata, qmdata.Name) hostConfig = getHostConfig(t, 4, qmsharedlogs, qmshareddata, volume)
} }
networkingConfig := network.NetworkingConfig{} networkingConfig := ce.ContainerNetworkSettings{}
qm, err := cli.ContainerCreate(context.Background(), &containerConfig, &hostConfig, &networkingConfig, t.Name()+id) qmID, err := cli.ContainerCreate(&containerConfig, &hostConfig, &networkingConfig, t.Name()+id)
if err != nil { if err != nil {
return err, "", "" return err, "", ""
} }
startContainer(t, cli, qm.ID) startContainer(t, cli, qmID)
return nil, qm.ID, qmdata.Name return nil, qmID, volume
} }
func getHostConfig(t *testing.T, mounts int, qmsharedlogs string, qmshareddata string, qmdata string) container.HostConfig { func getHostConfig(t *testing.T, mounts int, qmsharedlogs string, qmshareddata string, qmdata string) ce.ContainerHostConfig {
var hostConfig container.HostConfig var hostConfig ce.ContainerHostConfig
switch mounts { switch mounts {
case 1: case 1:
hostConfig = container.HostConfig{ hostConfig = ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t),
qmdata + ":/mnt/mqm", qmdata + ":/mnt/mqm",
}, },
} }
case 2: case 2:
hostConfig = container.HostConfig{ hostConfig = ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t),
qmdata + ":/mnt/mqm", qmdata + ":/mnt/mqm",
qmshareddata + ":/mnt/mqm-data", qmshareddata + ":/mnt/mqm-data",
}, },
} }
case 3: case 3:
hostConfig = container.HostConfig{ hostConfig = ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t),
qmdata + ":/mnt/mqm", qmdata + ":/mnt/mqm",
qmsharedlogs + ":/mnt/mqm-log", qmsharedlogs + ":/mnt/mqm-log",
}, },
} }
case 4: case 4:
hostConfig = container.HostConfig{ hostConfig = ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t),
qmdata + ":/mnt/mqm", qmdata + ":/mnt/mqm",
qmsharedlogs + ":/mnt/mqm-log", qmsharedlogs + ":/mnt/mqm-log",
qmshareddata + ":/mnt/mqm-data", qmshareddata + ":/mnt/mqm-data",
}, },
} }
} }
if coverage() {
hostConfig.Binds = append(hostConfig.Binds, coverageBind(t))
}
return hostConfig return hostConfig
} }
func startContainer(t *testing.T, cli *client.Client, ID string) { func startContainer(t *testing.T, cli ce.ContainerInterface, ID string) {
t.Logf("Starting container: %v", ID) t.Logf("Starting container: %v", ID)
startOptions := types.ContainerStartOptions{} startOptions := ce.ContainerStartOptions{}
err := cli.ContainerStart(context.Background(), ID, startOptions) err := cli.ContainerStart(ID, startOptions)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
} }
func stopContainer(t *testing.T, cli *client.Client, ID string) { func stopContainer(t *testing.T, cli ce.ContainerInterface, ID string) {
t.Logf("Stopping container: %v", ID) t.Logf("Stopping container: %v", ID)
timeout := 10 * time.Second timeout := 10 * time.Second
err := cli.ContainerStop(context.Background(), ID, &timeout) //Duration(20)*time.Second) err := cli.ContainerStop(ID, &timeout) //Duration(20)*time.Second)
if err != nil { if err != nil {
t.Fatal(err) // Just log the error and continue
t.Log(err)
} }
} }
func killContainer(t *testing.T, cli *client.Client, ID string, signal string) { func killContainer(t *testing.T, cli ce.ContainerInterface, ID string, signal string) {
t.Logf("Killing container: %v", ID) t.Logf("Killing container: %v", ID)
err := cli.ContainerKill(context.Background(), ID, signal) err := cli.ContainerKill(ID, signal)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -545,17 +521,17 @@ func getCoverageExitCode(t *testing.T, orig int64) int64 {
} }
// waitForContainer waits until a container has exited // waitForContainer waits until a container has exited
func waitForContainer(t *testing.T, cli *client.Client, ID string, timeout time.Duration) int64 { func waitForContainer(t *testing.T, cli ce.ContainerInterface, ID string, timeout time.Duration) int64 {
c, cancel := context.WithTimeout(context.Background(), timeout) c, cancel := context.WithTimeout(context.Background(), timeout)
defer cancel() defer cancel()
t.Logf("Waiting for container for %s", timeout) t.Logf("Waiting for container for %s", timeout)
okC, errC := cli.ContainerWait(c, ID, container.WaitConditionNotRunning) okC, errC := cli.ContainerWait(c, ID, ce.ContainerStateNotRunning)
var rc int64 var rc int64
select { select {
case err := <-errC: case err := <-errC:
t.Fatal(err) t.Fatal(err)
case ok := <-okC: case ok := <-okC:
rc = ok.StatusCode rc = ok
} }
if coverage() { if coverage() {
// COVERAGE: When running coverage, the exit code is written to a file, // COVERAGE: When running coverage, the exit code is written to a file,
@@ -567,78 +543,15 @@ func waitForContainer(t *testing.T, cli *client.Client, ID string, timeout time.
} }
// execContainer runs a command in a running container, and returns the exit code and output // execContainer runs a command in a running container, and returns the exit code and output
func execContainer(t *testing.T, cli *client.Client, ID string, user string, cmd []string) (int, string) { func execContainer(t *testing.T, cli ce.ContainerInterface, ID string, user string, cmd []string) (int, string) {
t.Logf("Running command: %v", cmd) t.Logf("Running command: %v", cmd)
config := types.ExecConfig{ exitcode, outputStr := cli.ExecContainer(ID, user, cmd)
User: user,
Privileged: false,
Tty: false,
AttachStdin: false,
// Note that you still need to attach stdout/stderr, even though they're not wanted
AttachStdout: true,
AttachStderr: true,
Detach: false,
Cmd: cmd,
}
resp, err := cli.ContainerExecCreate(context.Background(), ID, config)
if err != nil {
t.Fatal(err)
}
hijack, err := cli.ContainerExecAttach(context.Background(), resp.ID, types.ExecStartCheck{})
if err != nil {
t.Fatal(err)
}
defer hijack.Close()
time.Sleep(time.Millisecond * 10)
err = cli.ContainerExecStart(context.Background(), resp.ID, types.ExecStartCheck{
Detach: false,
Tty: false,
})
if err != nil {
t.Fatal(err)
}
// Wait for the command to finish
var exitcode int
var outputStr string
for {
inspect, err := cli.ContainerExecInspect(context.Background(), resp.ID)
if err != nil {
t.Fatal(err)
}
if inspect.Running {
continue
}
exitcode = inspect.ExitCode
buf := new(bytes.Buffer)
// Each output line has a header, which needs to be removed
_, err = stdcopy.StdCopy(buf, buf, hijack.Reader)
if err != nil {
t.Fatal(err)
}
outputStr = strings.TrimSpace(buf.String())
/* Commented out on 14/06/2018 as it might not be needed after adding
* pause between ContainerExecAttach and ContainerExecStart.
* TODO If intermittent failures do not occur, remove and refactor.
*
* // Before we go let's just double check it did actually finish running
* // because sometimes we get a "Exec command already running error"
* alreadyRunningErr := regexp.MustCompile("Error: Exec command .* is already running")
* if alreadyRunningErr.MatchString(outputStr) {
* continue
* }
*/
break
}
return exitcode, outputStr return exitcode, outputStr
} }
func waitForReady(t *testing.T, cli *client.Client, ID string) { func waitForReady(t *testing.T, cli ce.ContainerInterface, ID string) {
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute) ctx, cancel := context.WithTimeout(context.Background(), 4*time.Minute)
defer cancel() defer cancel()
for { for {
@@ -662,57 +575,47 @@ func waitForReady(t *testing.T, cli *client.Client, ID string) {
} }
} }
func getIPAddress(t *testing.T, cli *client.Client, ID string) string { func createNetwork(t *testing.T, cli ce.ContainerInterface) string {
ctr, err := cli.ContainerInspect(context.Background(), ID)
if err != nil {
t.Fatal(err)
}
return ctr.NetworkSettings.IPAddress
}
func createNetwork(t *testing.T, cli *client.Client) string {
name := "test" name := "test"
t.Logf("Creating network: %v", name) t.Logf("Creating network: %v", name)
opts := types.NetworkCreate{} opts := ce.NetworkCreateOptions{}
net, err := cli.NetworkCreate(context.Background(), name, opts) netID, err := cli.NetworkCreate(name, opts)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
t.Logf("Created network %v with ID %v", name, net.ID) t.Logf("Created network %v with ID %v", name, netID)
return net.ID return netID
} }
func removeNetwork(t *testing.T, cli *client.Client, ID string) { func removeNetwork(t *testing.T, cli ce.ContainerInterface, ID string) {
t.Logf("Removing network ID: %v", ID) t.Logf("Removing network ID: %v", ID)
err := cli.NetworkRemove(context.Background(), ID) err := cli.NetworkRemove(ID)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
} }
func createVolume(t *testing.T, cli *client.Client, name string) types.Volume { func createVolume(t *testing.T, cli ce.ContainerInterface, name string) string {
v, err := cli.VolumeCreate(context.Background(), volume.VolumeCreateBody{ v, err := cli.VolumeCreate(ce.VolumeCreateOptions{
Driver: "local", Driver: "local",
DriverOpts: map[string]string{},
Labels: map[string]string{},
Name: name, Name: name,
}) })
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
t.Logf("Created volume %v", v.Name) t.Logf("Created volume %v", v)
return v return v
} }
func removeVolume(t *testing.T, cli *client.Client, name string) { func removeVolume(t *testing.T, cli ce.ContainerInterface, name string) {
t.Logf("Removing volume %v", name) t.Logf("Removing volume %v", name)
err := cli.VolumeRemove(context.Background(), name, true) err := cli.VolumeRemove(name, true)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
} }
func inspectTextLogs(t *testing.T, cli *client.Client, ID string) string { func inspectTextLogs(t *testing.T, cli ce.ContainerInterface, ID string) string {
jsonLogs := inspectLogs(t, cli, ID) jsonLogs := inspectLogs(t, cli, ID)
scanner := bufio.NewScanner(strings.NewReader(jsonLogs)) scanner := bufio.NewScanner(strings.NewReader(jsonLogs))
b := make([]byte, 64*1024) b := make([]byte, 64*1024)
@@ -720,9 +623,11 @@ func inspectTextLogs(t *testing.T, cli *client.Client, ID string) string {
for scanner.Scan() { for scanner.Scan() {
text := scanner.Text() text := scanner.Text()
if strings.HasPrefix(text, "{") { if strings.HasPrefix(text, "{") {
// If it's a JSON log message, it makes it hard to debug the test, as the JSON
// is embedded in the long test output. So just summarize the JSON instead.
var e map[string]interface{} var e map[string]interface{}
json.Unmarshal([]byte(text), &e) json.Unmarshal([]byte(text), &e)
fmt.Fprintf(buf, "{\"message\": \"%v\"}\n", e["message"]) fmt.Fprintf(buf, "{\"ibm_datetime\": \"%v\", \"message\": \"%v\", ...}\n", e["ibm_datetime"], e["message"])
} else { } else {
fmt.Fprintln(buf, text) fmt.Fprintln(buf, text)
} }
@@ -734,24 +639,14 @@ func inspectTextLogs(t *testing.T, cli *client.Client, ID string) string {
return buf.String() return buf.String()
} }
func inspectLogs(t *testing.T, cli *client.Client, ID string) string { func inspectLogs(t *testing.T, cli ce.ContainerInterface, ID string) string {
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
defer cancel() defer cancel()
reader, err := cli.ContainerLogs(ctx, ID, types.ContainerLogsOptions{ logs, err := cli.GetContainerLogs(ctx, ID, ce.ContainerLogsOptions{})
ShowStdout: true,
ShowStderr: true,
})
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
buf := new(bytes.Buffer) return logs
// Each output line has a header, which needs to be removed
_, err = stdcopy.StdCopy(buf, buf, reader)
if err != nil {
t.Fatal(err)
}
return buf.String()
} }
// generateTAR creates a TAR-formatted []byte, with the specified files included. // generateTAR creates a TAR-formatted []byte, with the specified files included.
@@ -781,76 +676,54 @@ func generateTAR(t *testing.T, files []struct{ Name, Body string }) []byte {
} }
// createImage creates a new Docker image with the specified files included. // createImage creates a new Docker image with the specified files included.
func createImage(t *testing.T, cli *client.Client, files []struct{ Name, Body string }) string { func createImage(t *testing.T, cli ce.ContainerInterface, files []struct{ Name, Body string }) string {
r := bytes.NewReader(generateTAR(t, files)) r := bytes.NewReader(generateTAR(t, files))
tag := strings.ToLower(t.Name()) tag := strings.ToLower(t.Name())
buildOptions := types.ImageBuildOptions{
Context: r, tmpDir, err := os.MkdirTemp("", "tmp")
Tags: []string{tag},
}
resp, err := cli.ImageBuild(context.Background(), r, buildOptions)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
// resp (ImageBuildResponse) contains a series of JSON messages
dec := json.NewDecoder(resp.Body) defer os.RemoveAll(tmpDir)
for {
m := jsonmessage.JSONMessage{} //Write files to temp directory
err := dec.Decode(&m) for _, file := range files {
if m.Error != nil { //Add tag to file name to allow parallel testing
t.Fatal(m.ErrorMessage) f, err := os.Create(filepath.Join(tmpDir, file.Name))
}
t.Log(strings.TrimSpace(m.Stream))
if err == io.EOF {
break
}
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
defer f.Close()
body := []byte(file.Body)
_, err = f.Write(body)
if err != nil {
t.Fatal(err)
}
}
_, err = cli.ImageBuild(r, tag, filepath.Join(tmpDir, files[0].Name))
if err != nil {
t.Fatal(err)
} }
return tag return tag
} }
// deleteImage deletes a Docker image // deleteImage deletes a Docker image
func deleteImage(t *testing.T, cli *client.Client, id string) { func deleteImage(t *testing.T, cli ce.ContainerInterface, id string) {
cli.ImageRemove(context.Background(), id, types.ImageRemoveOptions{ cli.ImageRemove(id, ce.ImageRemoveOptions{
Force: true, Force: true,
}) })
} }
func copyFromContainer(t *testing.T, cli *client.Client, id string, file string) []byte { func copyFromContainer(t *testing.T, cli ce.ContainerInterface, id string, file string) []byte {
reader, _, err := cli.CopyFromContainer(context.Background(), id, file) b, err := cli.CopyFromContainer(id, file)
if err != nil {
t.Fatal(err)
}
defer reader.Close()
b, err := ioutil.ReadAll(reader)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
return b return b
} }
func getPort(t *testing.T, cli *client.Client, ID string, port int) string {
var inspectInfo types.ContainerJSON
var err error
for attemptsRemaining := 3; attemptsRemaining > 0; attemptsRemaining-- {
inspectInfo, err = cli.ContainerInspect(context.Background(), ID)
if err != nil {
t.Fatal(err)
}
portNat := nat.Port(fmt.Sprintf("%d/tcp", port))
if inspectInfo.NetworkSettings.Ports[portNat] == nil || len(inspectInfo.NetworkSettings.Ports[portNat]) == 0 {
t.Log("Container port not yet bound")
time.Sleep(1 * time.Second)
continue
}
return inspectInfo.NetworkSettings.Ports[portNat][0].HostPort
}
t.Fatal("Failed to get port")
return ""
}
func countLines(t *testing.T, r io.Reader) int { func countLines(t *testing.T, r io.Reader) int {
scanner := bufio.NewScanner(r) scanner := bufio.NewScanner(r)
count := 0 count := 0
@@ -882,15 +755,6 @@ func countTarLines(t *testing.T, b []byte) int {
return total return total
} }
func getMQVersion(t *testing.T, cli *client.Client) (string, error) {
inspect, _, err := cli.ImageInspectWithRaw(context.Background(), imageName())
if err != nil {
return "", err
}
version := inspect.ContainerConfig.Labels["version"]
return version, nil
}
// scanForExcludedEntries scans for default excluded messages // scanForExcludedEntries scans for default excluded messages
func scanForExcludedEntries(msg string) bool { func scanForExcludedEntries(msg string) bool {
if strings.Contains(msg, "AMQ5041I") || strings.Contains(msg, "AMQ5052I") || if strings.Contains(msg, "AMQ5041I") || strings.Contains(msg, "AMQ5052I") ||
@@ -917,7 +781,7 @@ func checkLogForValidJSON(jsonLogs string) bool {
// runContainerWithAllConfig creates and starts a container, using the supplied ContainerConfig, HostConfig, // runContainerWithAllConfig creates and starts a container, using the supplied ContainerConfig, HostConfig,
// NetworkingConfig, and container name (or the value of t.Name if containerName=""). // NetworkingConfig, and container name (or the value of t.Name if containerName="").
func runContainerWithAllConfigError(t *testing.T, cli *client.Client, containerConfig *container.Config, hostConfig *container.HostConfig, networkingConfig *network.NetworkingConfig, containerName string) (string, error) { func runContainerWithAllConfigError(t *testing.T, cli ce.ContainerInterface, containerConfig *ce.ContainerConfig, hostConfig *ce.ContainerHostConfig, networkingConfig *ce.ContainerNetworkSettings, containerName string) (string, error) {
if containerName == "" { if containerName == "" {
containerName = t.Name() containerName = t.Name()
} }
@@ -928,25 +792,26 @@ func runContainerWithAllConfigError(t *testing.T, cli *client.Client, containerC
if containerConfig.User == "" { if containerConfig.User == "" {
containerConfig.User = generateRandomUID() containerConfig.User = generateRandomUID()
} }
// if coverage if coverage() {
containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov") containerConfig.Env = append(containerConfig.Env, "COVERAGE_FILE="+t.Name()+".cov")
containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t)) containerConfig.Env = append(containerConfig.Env, "EXIT_CODE_FILE="+getExitCodeFilename(t))
}
t.Logf("Running container (%s)", containerConfig.Image) t.Logf("Running container (%s)", containerConfig.Image)
ctr, err := cli.ContainerCreate(context.Background(), containerConfig, hostConfig, networkingConfig, containerName) ID, err := cli.ContainerCreate(containerConfig, hostConfig, networkingConfig, containerName)
if err != nil { if err != nil {
return "", err return "", err
} }
err = startContainerError(t, cli, ctr.ID) err = startContainerError(t, cli, ID)
if err != nil { if err != nil {
return "", err return "", err
} }
return ctr.ID, nil return ID, nil
} }
func startContainerError(t *testing.T, cli *client.Client, ID string) error { func startContainerError(t *testing.T, cli ce.ContainerInterface, ID string) error {
t.Logf("Starting container: %v", ID) t.Logf("Starting container: %v", ID)
startOptions := types.ContainerStartOptions{} startOptions := ce.ContainerStartOptions{}
err := cli.ContainerStart(context.Background(), ID, startOptions) err := cli.ContainerStart(ID, startOptions)
if err != nil { if err != nil {
return err return err
} }
@@ -955,7 +820,7 @@ func startContainerError(t *testing.T, cli *client.Client, ID string) error {
} }
// testLogFilePages validates that the specified number of logFilePages is present in the qm.ini file. // testLogFilePages validates that the specified number of logFilePages is present in the qm.ini file.
func testLogFilePages(t *testing.T, cli *client.Client, id string, qmName string, expectedLogFilePages string) { func testLogFilePages(t *testing.T, cli ce.ContainerInterface, id string, qmName string, expectedLogFilePages string) {
catIniFileCommand := fmt.Sprintf("cat /var/mqm/qmgrs/" + qmName + "/qm.ini") catIniFileCommand := fmt.Sprintf("cat /var/mqm/qmgrs/" + qmName + "/qm.ini")
_, iniContent := execContainer(t, cli, id, "", []string{"bash", "-c", catIniFileCommand}) _, iniContent := execContainer(t, cli, id, "", []string{"bash", "-c", catIniFileCommand})
@@ -965,7 +830,7 @@ func testLogFilePages(t *testing.T, cli *client.Client, id string, qmName string
} }
// waitForMessageInLog will check for a particular message with wait // waitForMessageInLog will check for a particular message with wait
func waitForMessageInLog(t *testing.T, cli *client.Client, id string, expecteMessageId string) (string, error) { func waitForMessageInLog(t *testing.T, cli ce.ContainerInterface, id string, expectedMessageId string) (string, error) {
var jsonLogs string var jsonLogs string
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute) ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute)
defer cancel() defer cancel()
@@ -973,11 +838,29 @@ func waitForMessageInLog(t *testing.T, cli *client.Client, id string, expecteMes
select { select {
case <-time.After(1 * time.Second): case <-time.After(1 * time.Second):
jsonLogs = inspectLogs(t, cli, id) jsonLogs = inspectLogs(t, cli, id)
if strings.Contains(jsonLogs, expecteMessageId) { if strings.Contains(jsonLogs, expectedMessageId) {
return jsonLogs, nil return jsonLogs, nil
} }
case <-ctx.Done(): case <-ctx.Done():
return "", fmt.Errorf("Expected message Id %s was not logged.", expecteMessageId) return "", fmt.Errorf("expected message Id %s was not logged", expectedMessageId)
}
}
}
// waitForMessageCountInLog will check for a particular message with wait and must occur exact number of times in log as specified by count
func waitForMessageCountInLog(t *testing.T, cli ce.ContainerInterface, id string, expectedMessageId string, count int) (string, error) {
var jsonLogs string
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute)
defer cancel()
for {
select {
case <-time.After(1 * time.Second):
jsonLogs = inspectLogs(t, cli, id)
if strings.Contains(jsonLogs, expectedMessageId) && strings.Count(jsonLogs, expectedMessageId) == count {
return jsonLogs, nil
}
case <-ctx.Done():
return "", fmt.Errorf("expected message Id %s was not logged or it was not logged %v times", expectedMessageId, count)
} }
} }
} }

3
test/container/go.mod Normal file
View File

@@ -0,0 +1,3 @@
module github.com/ibm-messaging/mq-container/test/container
go 1.19

0
test/container/go.sum Normal file
View File

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2019, 2022 © Copyright IBM Corporation 2019, 2023
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.
@@ -21,7 +21,7 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/client" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
) )
var miEnv = []string{ var miEnv = []string{
@@ -34,10 +34,7 @@ var miEnv = []string{
// and starts/stop them checking we always have an active and standby // and starts/stop them checking we always have an active and standby
func TestMultiInstanceStartStop(t *testing.T) { func TestMultiInstanceStartStop(t *testing.T) {
t.Skipf("Skipping %v until test defect fixed", t.Name()) t.Skipf("Skipping %v until test defect fixed", t.Name())
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
err, qm1aId, qm1bId, volumes := configureMultiInstance(t, cli) err, qm1aId, qm1bId, volumes := configureMultiInstance(t, cli)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
@@ -76,10 +73,7 @@ func TestMultiInstanceStartStop(t *testing.T) {
// TestMultiInstanceContainerStop starts 2 containers in a multi instance queue manager configuration, // TestMultiInstanceContainerStop starts 2 containers in a multi instance queue manager configuration,
// stops the active queue manager, then checks to ensure the backup queue manager becomes active // stops the active queue manager, then checks to ensure the backup queue manager becomes active
func TestMultiInstanceContainerStop(t *testing.T) { func TestMultiInstanceContainerStop(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
err, qm1aId, qm1bId, volumes := configureMultiInstance(t, cli) err, qm1aId, qm1bId, volumes := configureMultiInstance(t, cli)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
@@ -122,21 +116,16 @@ func TestMultiInstanceContainerStop(t *testing.T) {
// configuration, then checks to ensure that both an active and standby queue manager have been started // configuration, then checks to ensure that both an active and standby queue manager have been started
func TestMultiInstanceRace(t *testing.T) { func TestMultiInstanceRace(t *testing.T) {
t.Skipf("Skipping %v until file lock is implemented", t.Name()) t.Skipf("Skipping %v until file lock is implemented", t.Name())
cli := ce.NewContainerClient()
cli, err := client.NewClientWithOpts(client.FromEnv)
if err != nil {
t.Fatal(err)
}
qmsharedlogs := createVolume(t, cli, "qmsharedlogs") qmsharedlogs := createVolume(t, cli, "qmsharedlogs")
defer removeVolume(t, cli, qmsharedlogs.Name) defer removeVolume(t, cli, qmsharedlogs)
qmshareddata := createVolume(t, cli, "qmshareddata") qmshareddata := createVolume(t, cli, "qmshareddata")
defer removeVolume(t, cli, qmshareddata.Name) defer removeVolume(t, cli, qmshareddata)
qmsChannel := make(chan QMChan) qmsChannel := make(chan QMChan)
go singleMultiInstanceQueueManager(t, cli, qmsharedlogs.Name, qmshareddata.Name, qmsChannel) go singleMultiInstanceQueueManager(t, cli, qmsharedlogs, qmshareddata, qmsChannel)
go singleMultiInstanceQueueManager(t, cli, qmsharedlogs.Name, qmshareddata.Name, qmsChannel) go singleMultiInstanceQueueManager(t, cli, qmsharedlogs, qmshareddata, qmsChannel)
qm1a := <-qmsChannel qm1a := <-qmsChannel
if qm1a.Error != nil { if qm1a.Error != nil {
@@ -159,7 +148,7 @@ func TestMultiInstanceRace(t *testing.T) {
waitForReady(t, cli, qm1aId) waitForReady(t, cli, qm1aId)
waitForReady(t, cli, qm1bId) waitForReady(t, cli, qm1bId)
err, _, _ = getActiveStandbyQueueManager(t, cli, qm1aId, qm1bId) err, _, _ := getActiveStandbyQueueManager(t, cli, qm1aId, qm1bId)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -169,10 +158,7 @@ func TestMultiInstanceRace(t *testing.T) {
// mounts, then checks to ensure that the container terminates with the expected message // mounts, then checks to ensure that the container terminates with the expected message
func TestMultiInstanceNoSharedMounts(t *testing.T) { func TestMultiInstanceNoSharedMounts(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, "", "", miEnv) err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, "", "", miEnv)
if err != nil { if err != nil {
@@ -188,15 +174,12 @@ func TestMultiInstanceNoSharedMounts(t *testing.T) {
// TestMultiInstanceNoSharedLogs starts 2 multi instance queue managers without providing a shared log // TestMultiInstanceNoSharedLogs starts 2 multi instance queue managers without providing a shared log
// mount, then checks to ensure that the container terminates with the expected message // mount, then checks to ensure that the container terminates with the expected message
func TestMultiInstanceNoSharedLogs(t *testing.T) { func TestMultiInstanceNoSharedLogs(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
qmshareddata := createVolume(t, cli, "qmshareddata") qmshareddata := createVolume(t, cli, "qmshareddata")
defer removeVolume(t, cli, qmshareddata.Name) defer removeVolume(t, cli, qmshareddata)
err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, "", qmshareddata.Name, miEnv) err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, "", qmshareddata, miEnv)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -210,15 +193,12 @@ func TestMultiInstanceNoSharedLogs(t *testing.T) {
// TestMultiInstanceNoSharedData starts 2 multi instance queue managers without providing a shared data // TestMultiInstanceNoSharedData starts 2 multi instance queue managers without providing a shared data
// mount, then checks to ensure that the container terminates with the expected message // mount, then checks to ensure that the container terminates with the expected message
func TestMultiInstanceNoSharedData(t *testing.T) { func TestMultiInstanceNoSharedData(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
qmsharedlogs := createVolume(t, cli, "qmsharedlogs") qmsharedlogs := createVolume(t, cli, "qmsharedlogs")
defer removeVolume(t, cli, qmsharedlogs.Name) defer removeVolume(t, cli, qmsharedlogs)
err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs.Name, "", miEnv) err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs, "", miEnv)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -232,10 +212,7 @@ func TestMultiInstanceNoSharedData(t *testing.T) {
// TestMultiInstanceNoMounts starts 2 multi instance queue managers without providing a shared data // TestMultiInstanceNoMounts starts 2 multi instance queue managers without providing a shared data
// mount, then checks to ensure that the container terminates with the expected message // mount, then checks to ensure that the container terminates with the expected message
func TestMultiInstanceNoMounts(t *testing.T) { func TestMultiInstanceNoMounts(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, false, "", "", miEnv) err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, false, "", "", miEnv)
if err != nil { if err != nil {

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2019, 2022 © Copyright IBM Corporation 2019, 2023
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.
@@ -23,7 +23,7 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/client" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
) )
type QMChan struct { type QMChan struct {
@@ -34,27 +34,27 @@ type QMChan struct {
// configureMultiInstance creates the volumes and containers required for basic testing // configureMultiInstance creates the volumes and containers required for basic testing
// of multi instance queue managers. Returns error, qm1a ID, qm1b ID, slice of volume names // of multi instance queue managers. Returns error, qm1a ID, qm1b ID, slice of volume names
func configureMultiInstance(t *testing.T, cli *client.Client) (error, string, string, []string) { func configureMultiInstance(t *testing.T, cli ce.ContainerInterface) (error, string, string, []string) {
qmsharedlogs := createVolume(t, cli, "qmsharedlogs") qmsharedlogs := createVolume(t, cli, "qmsharedlogs")
qmshareddata := createVolume(t, cli, "qmshareddata") qmshareddata := createVolume(t, cli, "qmshareddata")
err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs.Name, qmshareddata.Name, miEnv) err, qm1aId, qm1aData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs, qmshareddata, miEnv)
if err != nil { if err != nil {
return err, "", "", []string{} return err, "", "", []string{}
} }
time.Sleep(10 * time.Second) time.Sleep(10 * time.Second)
err, qm1bId, qm1bData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs.Name, qmshareddata.Name, miEnv) err, qm1bId, qm1bData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs, qmshareddata, miEnv)
if err != nil { if err != nil {
return err, "", "", []string{} return err, "", "", []string{}
} }
volumes := []string{qmsharedlogs.Name, qmshareddata.Name, qm1aData, qm1bData} volumes := []string{qmsharedlogs, qmshareddata, qm1aData, qm1bData}
return nil, qm1aId, qm1bId, volumes return nil, qm1aId, qm1bId, volumes
} }
func singleMultiInstanceQueueManager(t *testing.T, cli *client.Client, qmsharedlogs string, qmshareddata string, qmsChannel chan QMChan) { func singleMultiInstanceQueueManager(t *testing.T, cli ce.ContainerInterface, qmsharedlogs string, qmshareddata string, qmsChannel chan QMChan) {
err, qmId, qmData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs, qmshareddata, miEnv) err, qmId, qmData := startMultiVolumeQueueManager(t, cli, true, qmsharedlogs, qmshareddata, miEnv)
if err != nil { if err != nil {
qmsChannel <- QMChan{Error: err} qmsChannel <- QMChan{Error: err}
@@ -62,7 +62,7 @@ func singleMultiInstanceQueueManager(t *testing.T, cli *client.Client, qmsharedl
qmsChannel <- QMChan{QMId: qmId, QMData: qmData} qmsChannel <- QMChan{QMId: qmId, QMData: qmData}
} }
func getActiveStandbyQueueManager(t *testing.T, cli *client.Client, qm1aId string, qm1bId string) (error, string, string) { func getActiveStandbyQueueManager(t *testing.T, cli ce.ContainerInterface, qm1aId string, qm1bId string) (error, string, string) {
qm1aStatus := getQueueManagerStatus(t, cli, qm1aId, "QM1") qm1aStatus := getQueueManagerStatus(t, cli, qm1aId, "QM1")
qm1bStatus := getQueueManagerStatus(t, cli, qm1bId, "QM1") qm1bStatus := getQueueManagerStatus(t, cli, qm1bId, "QM1")
@@ -75,7 +75,7 @@ func getActiveStandbyQueueManager(t *testing.T, cli *client.Client, qm1aId strin
return err, "", "" return err, "", ""
} }
func getQueueManagerStatus(t *testing.T, cli *client.Client, containerID string, queueManagerName string) string { func getQueueManagerStatus(t *testing.T, cli ce.ContainerInterface, containerID string, queueManagerName string) string {
_, dspmqOut := execContainer(t, cli, containerID, "", []string{"bash", "-c", "dspmq", "-m", queueManagerName}) _, dspmqOut := execContainer(t, cli, containerID, "", []string{"bash", "-c", "dspmq", "-m", queueManagerName})
t.Logf("dspmq for %v (%v) returned: %v", containerID, queueManagerName, dspmqOut) t.Logf("dspmq for %v (%v) returned: %v", containerID, queueManagerName, dspmqOut)
regex := regexp.MustCompile(`STATUS\(.*\)`) regex := regexp.MustCompile(`STATUS\(.*\)`)
@@ -84,7 +84,7 @@ func getQueueManagerStatus(t *testing.T, cli *client.Client, containerID string,
return status return status
} }
func waitForTerminationMessage(t *testing.T, cli *client.Client, qmId string, terminationString string, timeout time.Duration) { func waitForTerminationMessage(t *testing.T, cli ce.ContainerInterface, qmId string, terminationString string, timeout time.Duration) {
ctx, cancel := context.WithTimeout(context.Background(), timeout) ctx, cancel := context.WithTimeout(context.Background(), timeout)
defer cancel() defer cancel()
for { for {
@@ -93,7 +93,7 @@ func waitForTerminationMessage(t *testing.T, cli *client.Client, qmId string, te
m := terminationMessage(t, cli, qmId) m := terminationMessage(t, cli, qmId)
if m != "" { if m != "" {
if !strings.Contains(m, terminationString) { if !strings.Contains(m, terminationString) {
t.Fatalf("Expected container to fail on missing required mount. Got termination message: %v", m) t.Fatalf("Expected container to fail with termination message %v. Got termination message: %v", terminationString, m)
} }
return return
} }

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2021, 2022 © Copyright IBM Corporation 2021, 2023
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.
@@ -16,20 +16,19 @@ limitations under the License.
package main package main
import ( import (
"github.com/docker/docker/client"
"strings" "strings"
"testing" "testing"
"time"
ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
) )
// TestNativeHABasic creates 3 containers in a Native HA queue manager configuration // TestNativeHABasic creates 3 containers in a Native HA queue manager configuration
// and ensures the queue manger and replicas start as expected // and ensures the queue manger and replicas start as expected
func TestNativeHABasic(t *testing.T) { func TestNativeHABasic(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -40,21 +39,18 @@ func TestNativeHABasic(t *testing.T) {
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmVolumes := []string{} qmVolumes := []string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
vol := createVolume(t, cli, containerNames[i]) vol := createVolume(t, cli, containerNames[i])
defer removeVolume(t, cli, vol.Name) defer removeVolume(t, cli, vol)
qmVolumes = append(qmVolumes, vol.Name) qmVolumes = append(qmVolumes, vol)
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, basePort)
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) hostConfig := getHostConfig(t, 1, "", "", vol)
hostConfig := getHostConfig(t, 1, "", "", vol.Name) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) networkingConfig := getNativeHANetworkConfig("host")
ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
@@ -74,12 +70,9 @@ func TestNativeHABasic(t *testing.T) {
// queue manager comes back as a replica // queue manager comes back as a replica
func TestNativeHAFailover(t *testing.T) { func TestNativeHAFailover(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -90,21 +83,18 @@ func TestNativeHAFailover(t *testing.T) {
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmVolumes := []string{} qmVolumes := []string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
vol := createVolume(t, cli, containerNames[i]) vol := createVolume(t, cli, containerNames[i])
defer removeVolume(t, cli, vol.Name) defer removeVolume(t, cli, vol)
qmVolumes = append(qmVolumes, vol.Name) qmVolumes = append(qmVolumes, vol)
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, basePort)
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) hostConfig := getHostConfig(t, 1, "", "", vol)
hostConfig := getHostConfig(t, 1, "", "", vol.Name) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) networkingConfig := getNativeHANetworkConfig("host")
ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
@@ -132,33 +122,31 @@ func TestNativeHAFailover(t *testing.T) {
// TestNativeHASecure creates 3 containers in a Native HA queue manager configuration // TestNativeHASecure creates 3 containers in a Native HA queue manager configuration
// with HA TLS enabled, and ensures the queue manger and replicas start as expected // with HA TLS enabled, and ensures the queue manger and replicas start as expected
func TestNativeHASecure(t *testing.T) { func TestNativeHASecure(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
if version < "9.2.2.0" { if version < "9.2.2.0" {
t.Skipf("Skipping %s as test requires at least MQ 9.2.2.0, but image is version %s", t.Name(), version) t.Skipf("Skipping %s as test requires at least MQ 9.2.2.0, but image is version %s", t.Name(), version)
} }
if isARM(t) {
t.Skip("Skipping as an issue has been identified for the arm64 MQ image")
}
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort)
containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true") containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true")
hostConfig := getNativeHASecureHostConfig(t) hostConfig := getNativeHASecureHostConfig(t)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig("host")
ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
@@ -177,12 +165,9 @@ func TestNativeHASecure(t *testing.T) {
// with HA TLS enabled, overrides the default CipherSpec, and ensures the queue manger // with HA TLS enabled, overrides the default CipherSpec, and ensures the queue manger
// and replicas start as expected // and replicas start as expected
func TestNativeHASecureCipherSpec(t *testing.T) { func TestNativeHASecureCipherSpec(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -192,18 +177,16 @@ func TestNativeHASecureCipherSpec(t *testing.T) {
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort)
containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=TLS_AES_256_GCM_SHA384") containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=TLS_AES_256_GCM_SHA384")
hostConfig := getNativeHASecureHostConfig(t) hostConfig := getNativeHASecureHostConfig(t)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig("host")
ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
@@ -222,12 +205,9 @@ func TestNativeHASecureCipherSpec(t *testing.T) {
// with HA TLS FIPS enabled, overrides the default CipherSpec, and ensures the queue manger // with HA TLS FIPS enabled, overrides the default CipherSpec, and ensures the queue manger
// and replicas start as expected. This test uses FIPS compliant cipher. // and replicas start as expected. This test uses FIPS compliant cipher.
func TestNativeHASecureCipherSpecFIPS(t *testing.T) { func TestNativeHASecureCipherSpecFIPS(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -237,19 +217,17 @@ func TestNativeHASecureCipherSpecFIPS(t *testing.T) {
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort)
// MQ_NATIVE_HA_CIPHERSPEC is set a FIPS compliant cipherspec. // MQ_NATIVE_HA_CIPHERSPEC is set a FIPS compliant cipherspec.
containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=TLS_RSA_WITH_AES_128_GCM_SHA256", "MQ_ENABLE_FIPS=true") containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=TLS_RSA_WITH_AES_128_GCM_SHA256", "MQ_ENABLE_FIPS=true")
hostConfig := getNativeHASecureHostConfig(t) hostConfig := getNativeHASecureHostConfig(t)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig("host")
ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
@@ -272,12 +250,9 @@ func TestNativeHASecureCipherSpecFIPS(t *testing.T) {
// with HA TLS FIPS enabled with non-FIPS cipher, overrides the default CipherSpec, and // with HA TLS FIPS enabled with non-FIPS cipher, overrides the default CipherSpec, and
// ensures the queue manger and replicas don't start as expected // ensures the queue manger and replicas don't start as expected
func TestNativeHASecureCipherSpecNonFIPSCipher(t *testing.T) { func TestNativeHASecureCipherSpecNonFIPSCipher(t *testing.T) {
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
version, err := getMQVersion(t, cli) version, err := cli.GetMQVersion(imageName())
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
@@ -287,26 +262,24 @@ func TestNativeHASecureCipherSpecNonFIPSCipher(t *testing.T) {
containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"} containerNames := [3]string{"QM1_1", "QM1_2", "QM1_3"}
qmReplicaIDs := [3]string{} qmReplicaIDs := [3]string{}
qmNetwork, err := createBridgeNetwork(cli, t) //Each native HA qmgr instance is exposed on subsequent ports on the host starting with basePort
if err != nil { //If the qmgr exposes more than one port (tests do not do this currently) then they are offset by +50
t.Fatal(err) basePort := 14551
}
defer removeBridgeNetwork(cli, qmNetwork.ID)
for i := 0; i <= 2; i++ { for i := 0; i <= 2; i++ {
nhaPort := basePort + i
containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort) containerConfig := getNativeHAContainerConfig(containerNames[i], containerNames, defaultHAPort)
// MQ_NATIVE_HA_CIPHERSPEC is set a FIPS non-compliant cipherspec - SSL_ECDHE_ECDSA_WITH_RC4_128_SHA // MQ_NATIVE_HA_CIPHERSPEC is set a FIPS non-compliant cipherspec - SSL_ECDHE_ECDSA_WITH_RC4_128_SHA
containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=TLS_RSA_WITH_AES_128_GCM_SHA256", "MQ_ENABLE_FIPS=true") containerConfig.Env = append(containerConfig.Env, "MQ_NATIVE_HA_TLS=true", "MQ_NATIVE_HA_CIPHERSPEC=SSL_ECDHE_ECDSA_WITH_RC4_128_SHA", "MQ_ENABLE_FIPS=true")
hostConfig := getNativeHASecureHostConfig(t) hostConfig := getNativeHASecureHostConfig(t)
networkingConfig := getNativeHANetworkConfig(qmNetwork.ID) hostConfig = populateNativeHAPortBindings([]int{9414}, nhaPort, hostConfig)
networkingConfig := getNativeHANetworkConfig("host")
ctr, err := runContainerWithAllConfigError(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i]) ctr := runContainerWithAllConfig(t, cli, &containerConfig, &hostConfig, &networkingConfig, containerNames[i])
defer cleanContainer(t, cli, ctr) defer cleanContainer(t, cli, ctr)
// We expect container to fail in this case because the cipher is non-FIPS and we have asked for FIPS compliance // We expect container to fail in this case because the cipher is non-FIPS and we have asked for FIPS compliance
// by setting MQ_ENABLE_FIPS=true // by setting MQ_ENABLE_FIPS=true
if err == nil {
t.Logf("Container start expected to fail but did not. %v", err)
}
qmReplicaIDs[i] = ctr qmReplicaIDs[i] = ctr
} }
for i := 0; i <= 2; i++ {
waitForTerminationMessage(t, cli, qmReplicaIDs[i], "/opt/mqm/bin/strmqm: exit status 23", 60*time.Second)
}
} }

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2021 © Copyright IBM Corporation 2021, 2023
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.
@@ -19,13 +19,11 @@ import (
"context" "context"
"fmt" "fmt"
"path/filepath" "path/filepath"
"strconv"
"testing" "testing"
"time" "time"
"github.com/docker/docker/api/types" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
"github.com/docker/docker/api/types/container"
"github.com/docker/docker/api/types/network"
"github.com/docker/docker/client"
) )
const defaultHAPort = 9414 const defaultHAPort = 9414
@@ -36,16 +34,8 @@ type HAReplicaStatus struct {
Replica [2]string Replica [2]string
} }
func createBridgeNetwork(cli *client.Client, t *testing.T) (types.NetworkCreateResponse, error) { func getNativeHAContainerConfig(containerName string, replicaNames [3]string, haPort int) ce.ContainerConfig {
return cli.NetworkCreate(context.Background(), t.Name(), types.NetworkCreate{}) return ce.ContainerConfig{
}
func removeBridgeNetwork(cli *client.Client, networkID string) error {
return cli.NetworkRemove(context.Background(), networkID)
}
func getNativeHAContainerConfig(containerName string, replicaNames [3]string, haPort int) container.Config {
return container.Config{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=QM1", "MQ_QMGR_NAME=QM1",
@@ -55,15 +45,18 @@ func getNativeHAContainerConfig(containerName string, replicaNames [3]string, ha
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_0_NAME=%s", replicaNames[0]), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_0_NAME=%s", replicaNames[0]),
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_1_NAME=%s", replicaNames[1]), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_1_NAME=%s", replicaNames[1]),
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_2_NAME=%s", replicaNames[2]), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_2_NAME=%s", replicaNames[2]),
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_0_REPLICATION_ADDRESS=%s(%d)", replicaNames[0], haPort), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_0_REPLICATION_ADDRESS=%s(%d)", "127.0.0.1", haPort+0),
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_1_REPLICATION_ADDRESS=%s(%d)", replicaNames[1], haPort), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_1_REPLICATION_ADDRESS=%s(%d)", "127.0.0.1", haPort+1),
fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_2_REPLICATION_ADDRESS=%s(%d)", replicaNames[2], haPort), fmt.Sprintf("MQ_NATIVE_HA_INSTANCE_2_REPLICATION_ADDRESS=%s(%d)", "127.0.0.1", haPort+2),
}, },
//When using the host for networking a consistent user was required. If a random user is used then the following example error was recorded.
//AMQ3209E: Native HA connection rejected due to configuration mismatch of 'QmgrUserId=5024'
User: "1111",
} }
} }
func getNativeHASecureHostConfig(t *testing.T) container.HostConfig { func getNativeHASecureHostConfig(t *testing.T) ce.ContainerHostConfig {
return container.HostConfig{ return ce.ContainerHostConfig{
Binds: []string{ Binds: []string{
coverageBind(t), coverageBind(t),
filepath.Join(getCwd(t, true), "../tls") + ":/etc/mqm/ha/pki/keys/ha", filepath.Join(getCwd(t, true), "../tls") + ":/etc/mqm/ha/pki/keys/ha",
@@ -71,15 +64,30 @@ func getNativeHASecureHostConfig(t *testing.T) container.HostConfig {
} }
} }
func getNativeHANetworkConfig(networkID string) network.NetworkingConfig { func getNativeHANetworkConfig(networkID string) ce.ContainerNetworkSettings {
return network.NetworkingConfig{ return ce.ContainerNetworkSettings{
EndpointsConfig: map[string]*network.EndpointSettings{ Networks: []string{networkID},
networkID: &network.EndpointSettings{},
},
} }
} }
func getActiveReplicaInstances(t *testing.T, cli *client.Client, qmReplicaIDs [3]string) (HAReplicaStatus, error) { // populatePortBindings writes port bindings to the host config
func populateNativeHAPortBindings(ports []int, nativeHaPort int, hostConfig ce.ContainerHostConfig) ce.ContainerHostConfig {
hostConfig.PortBindings = []ce.PortBinding{}
var binding ce.PortBinding
for i, p := range ports {
port := fmt.Sprintf("%v/tcp", p)
binding = ce.PortBinding{
ContainerPort: port,
HostIP: "0.0.0.0",
//Offset the ports by 50 if there are multiple
HostPort: strconv.Itoa(nativeHaPort + 50*i),
}
hostConfig.PortBindings = append(hostConfig.PortBindings, binding)
}
return hostConfig
}
func getActiveReplicaInstances(t *testing.T, cli ce.ContainerInterface, qmReplicaIDs [3]string) (HAReplicaStatus, error) {
var actives []string var actives []string
var replicas []string var replicas []string
@@ -104,7 +112,7 @@ func getActiveReplicaInstances(t *testing.T, cli *client.Client, qmReplicaIDs [3
return HAReplicaStatus{actives[0], [2]string{replicas[0], replicas[1]}}, nil return HAReplicaStatus{actives[0], [2]string{replicas[0], replicas[1]}}, nil
} }
func waitForReadyHA(t *testing.T, cli *client.Client, qmReplicaIDs [3]string) { func waitForReadyHA(t *testing.T, cli ce.ContainerInterface, qmReplicaIDs [3]string) {
ctx, cancel := context.WithTimeout(context.Background(), 4*time.Minute) ctx, cancel := context.WithTimeout(context.Background(), 4*time.Minute)
defer cancel() defer cancel()
@@ -129,7 +137,7 @@ func waitForReadyHA(t *testing.T, cli *client.Client, qmReplicaIDs [3]string) {
} }
} }
func waitForFailoverHA(t *testing.T, cli *client.Client, replicas [2]string) { func waitForFailoverHA(t *testing.T, cli ce.ContainerInterface, replicas [2]string) {
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute) ctx, cancel := context.WithTimeout(context.Background(), 2*time.Minute)
defer cancel() defer cancel()

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2018, 2022 © Copyright IBM Corporation 2018, 2023
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,20 +22,20 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/client" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
) )
func TestGoldenPathMetric(t *testing.T) { func TestGoldenPathMetric(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort}) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort) port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -55,14 +55,14 @@ func TestGoldenPathMetric(t *testing.T) {
func TestMetricNames(t *testing.T) { func TestMetricNames(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort}) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort) port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -99,14 +99,14 @@ func TestMetricNames(t *testing.T) {
func TestMetricLabels(t *testing.T) { func TestMetricLabels(t *testing.T) {
t.Parallel() t.Parallel()
cli := ce.NewContainerClient()
requiredLabels := []string{"qmgr"} requiredLabels := []string{"qmgr"}
cli, err := client.NewClientWithOpts(client.FromEnv) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort)
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -148,13 +148,13 @@ func TestMetricLabels(t *testing.T) {
func TestRapidFirePrometheus(t *testing.T) { func TestRapidFirePrometheus(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort)
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -182,13 +182,13 @@ func TestRapidFirePrometheus(t *testing.T) {
func TestSlowPrometheus(t *testing.T) { func TestSlowPrometheus(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort)
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -213,15 +213,14 @@ func TestSlowPrometheus(t *testing.T) {
func TestContainerRestart(t *testing.T) { func TestContainerRestart(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort)
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -239,7 +238,10 @@ func TestContainerRestart(t *testing.T) {
stopContainer(t, cli, id) stopContainer(t, cli, id)
// Start the container cleanly // Start the container cleanly
startContainer(t, cli, id) startContainer(t, cli, id)
port = getPort(t, cli, id, defaultMetricPort) port, err = cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -261,15 +263,14 @@ func TestContainerRestart(t *testing.T) {
func TestQMRestart(t *testing.T) { func TestQMRestart(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort}) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort) port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -319,14 +320,14 @@ func TestQMRestart(t *testing.T) {
func TestValidValues(t *testing.T) { func TestValidValues(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort}) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{defaultMetricPort})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
// hostname := getIPAddress(t, cli, id) // hostname := getIPAddress(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort) port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -343,7 +344,7 @@ func TestValidValues(t *testing.T) {
// Check that the values for each metric are valid numbers // Check that the values for each metric are valid numbers
// can be either int, float or exponential - all these can be parsed by ParseFloat function // can be either int, float or exponential - all these can be parsed by ParseFloat function
for _, e := range metrics { for _, e := range metrics {
if _, err = strconv.ParseFloat(e.Value, 64); err != nil { if _, err := strconv.ParseFloat(e.Value, 64); err != nil {
t.Errorf("Value (%s) for key (%s) is not a valid number", e.Value, e.Key) t.Errorf("Value (%s) for key (%s) is not a valid number", e.Value, e.Key)
} }
} }
@@ -355,14 +356,14 @@ func TestValidValues(t *testing.T) {
func TestChangingValues(t *testing.T) { func TestChangingValues(t *testing.T) {
t.Parallel() t.Parallel()
cli, err := client.NewClientWithOpts(client.FromEnv) cli := ce.NewContainerClient()
if err != nil {
t.Fatal(err)
}
id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{1414, defaultMetricPort}) id := runContainerWithPorts(t, cli, metricsContainerConfig(), []int{1414, defaultMetricPort})
defer cleanContainer(t, cli, id) defer cleanContainer(t, cli, id)
// hostname := getIPAddress(t, cli, id) // hostname := getIPAddress(t, cli, id)
port := getPort(t, cli, id, defaultMetricPort) port, err := cli.GetContainerPort(id, defaultMetricPort)
if err != nil {
t.Fatal(err)
}
// Now the container is ready we prod the prometheus endpoint until it's up. // Now the container is ready we prod the prometheus endpoint until it's up.
waitForMetricReady(t, port) waitForMetricReady(t, port)
@@ -386,7 +387,11 @@ func TestChangingValues(t *testing.T) {
} }
// Send invalid data to the MQ listener to generate a FDC // Send invalid data to the MQ listener to generate a FDC
listener := fmt.Sprintf("localhost:%s", getPort(t, cli, id, 1414)) noport, err := cli.GetContainerPort(id, 1414)
if err != nil {
t.Fatal(err)
}
listener := fmt.Sprintf("localhost:%s", noport)
conn, err := net.Dial("tcp", listener) conn, err := net.Dial("tcp", listener)
if err != nil { if err != nil {
t.Fatalf("Could not connect to the listener - %v", err) t.Fatalf("Could not connect to the listener - %v", err)

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2018 © Copyright IBM Corporation 2018, 2023
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.
@@ -24,7 +24,7 @@ import (
"testing" "testing"
"time" "time"
"github.com/docker/docker/api/types/container" ce "github.com/ibm-messaging/mq-container/test/container/containerengine"
) )
type mqmetric struct { type mqmetric struct {
@@ -146,8 +146,8 @@ func waitForMetricReady(t *testing.T, port string) {
t.Fatalf("Metric endpoint failed to startup in timely manner") t.Fatalf("Metric endpoint failed to startup in timely manner")
} }
func metricsContainerConfig() *container.Config { func metricsContainerConfig() *ce.ContainerConfig {
return &container.Config{ return &ce.ContainerConfig{
Env: []string{ Env: []string{
"LICENSE=accept", "LICENSE=accept",
"MQ_QMGR_NAME=" + defaultMetricQMName, "MQ_QMGR_NAME=" + defaultMetricQMName,

View File

@@ -1,40 +0,0 @@
module github.com/ibm-messaging/mq-container/test/docker
go 1.18
require (
// Note: This is not actually Docker v17.12!
// Go modules require the use of semver, but Docker does not use semver and has not
// [opted-in to use Go modules](https://github.com/golang/go/wiki/Modules#can-a-module-consume-a-package-that-has-not-opted-in-to-modules)
// This means that when you `go get` Docker, you need to do so based on a commit,
// e.g. `go get -v github.com/docker/docker@420b1d36250f9cfdc561f086f25a213ecb669b6f`,
// which uses the commit for [Docker v19.03.15](https://github.com/moby/moby/releases/tag/v19.03.15)
// Go will then find the latest tag with a semver-compatible tag. In Docker's case,
// v17.12.0 is valid semver, but v18.09 and v19.03 are not.
// Also note: Docker v20.10 is valid semver, but the v20.10 client API requires use of Docker API
// version 1.41 on the server, which is currently too new for the version of Docker in Travis (Ubuntu Bionic)
github.com/docker/docker v17.12.0-ce-rc1.0.20210128214336-420b1d36250f+incompatible
github.com/docker/go-connections v0.4.0
)
require (
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161 // indirect
github.com/Microsoft/go-winio v0.5.1 // indirect
github.com/containerd/containerd v1.6.6 // indirect
github.com/docker/distribution v2.8.1+incompatible // indirect
github.com/docker/go-units v0.4.0 // indirect
github.com/gogo/protobuf v1.3.2 // indirect
github.com/golang/protobuf v1.5.2 // indirect
github.com/gorilla/mux v1.8.0 // indirect
github.com/morikuni/aec v1.0.0 // indirect
github.com/opencontainers/go-digest v1.0.0 // indirect
github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799 // indirect
github.com/pkg/errors v0.9.1 // indirect
github.com/sirupsen/logrus v1.8.1 // indirect
golang.org/x/net v0.0.0-20211216030914-fe4d6282115f // indirect
golang.org/x/sys v0.0.0-20220422013727-9388b58f7150 // indirect
google.golang.org/genproto v0.0.0-20211208223120-3a66f561d7aa // indirect
google.golang.org/grpc v1.46.0 // indirect
google.golang.org/protobuf v1.27.1 // indirect
gotest.tools v2.2.0+incompatible // indirect
)

View File

@@ -1,199 +0,0 @@
cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161 h1:L/gRVlceqvL25UVaW/CKtUDjefjrs0SPonmDGUVOYP0=
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161/go.mod h1:xomTg63KZ2rFqZQzSB4Vz2SUXa1BpHTVz9L5PTmPC4E=
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
github.com/Microsoft/go-winio v0.5.1 h1:aPJp2QD7OOrhO5tQXqQoGSJc+DjDtWTGLOmNyAm6FgY=
github.com/Microsoft/go-winio v0.5.1/go.mod h1:JPGBdM1cNvN/6ISo+n8V5iA4v8pBzdOpzfwIujj1a84=
github.com/OneOfOne/xxhash v1.2.2/go.mod h1:HSdplMjZKSmBqAxg5vPj2TmRDmfkzw+cTzAElWljhcU=
github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY=
github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU=
github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc=
github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc=
github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk=
github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4/go.mod h1:6pvJx4me5XPnfI9Z40ddWsdw2W/uZgQLFXToKeRcDiI=
github.com/cncf/xds/go v0.0.0-20210312221358-fbca930ec8ed/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs=
github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs=
github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs=
github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs=
github.com/containerd/containerd v1.6.6 h1:xJNPhbrmz8xAMDNoVjHy9YHtWwEQNS+CDkcIRh7t8Y0=
github.com/containerd/containerd v1.6.6/go.mod h1:ZoP1geJldzCVY3Tonoz7b1IXk8rIX0Nltt5QE4OMNk0=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/docker/distribution v2.8.1+incompatible h1:Q50tZOPR6T/hjNsyc9g8/syEs6bk8XXApsHjKukMl68=
github.com/docker/distribution v2.8.1+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w=
github.com/docker/docker v17.12.0-ce-rc1.0.20210128214336-420b1d36250f+incompatible h1:nhVo1udYfMj0Jsw0lnqrTjjf33aLpdgW9Wve9fHVzhQ=
github.com/docker/docker v17.12.0-ce-rc1.0.20210128214336-420b1d36250f+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk=
github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ=
github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5XhDvyHbTtUxmeec=
github.com/docker/go-units v0.4.0 h1:3uh0PgVws3nIA0Q+MwDC8yjEPf9zjRfZZWXZYDct3Tw=
github.com/docker/go-units v0.4.0/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk=
github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4=
github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98=
github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk=
github.com/envoyproxy/go-control-plane v0.9.9-0.20210512163311-63b5d3c536b0/go.mod h1:hliV/p42l8fGbc6Y9bQ70uLwIvmJyVE5k4iMKlh8wCQ=
github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE=
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q=
github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q=
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
github.com/golang/protobuf v1.3.3/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw=
github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8=
github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA=
github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs=
github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w=
github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0=
github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8=
github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
github.com/golang/protobuf v1.4.3/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI=
github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk=
github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw=
github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY=
github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/go-cmp v0.5.6 h1:BKbKCqvP6I+rmFHt06ZmyQtvB8xAkWdhFyr0ZUNZcxQ=
github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE=
github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
github.com/gorilla/mux v1.8.0 h1:i40aqfkR1h2SlN9hojwV5ZA91wcXFOvkdNIeFDP5koI=
github.com/gorilla/mux v1.8.0/go.mod h1:DVbg23sWSpFRCP0SfiEN6jmj59UnW/n46BH5rLB71So=
github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw=
github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8=
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
github.com/morikuni/aec v1.0.0 h1:nP9CBfwrvYnBRgY6qfDQkygYDmYwOilePFkwzv4dU8A=
github.com/morikuni/aec v1.0.0/go.mod h1:BbKIizmSmc5MMPqRYbxO4ZU0S0+P200+tUnFx7PXmsc=
github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U=
github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM=
github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799 h1:rc3tiVYb5z54aKaDfakKn0dDjIyPpTtszkjuMzyt7ec=
github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0=
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ=
github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0=
github.com/sirupsen/logrus v1.8.1 h1:dJKuHgqk1NNQlqoA6BTlM1Wf9DOH3NBjQyu0h9+AZZE=
github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0=
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY=
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI=
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU=
golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
golang.org/x/net v0.0.0-20211216030914-fe4d6282115f h1:hEYJvxw1lSnWIl8X9ofsYMklzaDs90JI2az5YMd4fPM=
golang.org/x/net v0.0.0-20211216030914-fe4d6282115f/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220422013727-9388b58f7150 h1:xHms4gcpe1YE7A3yIllJXP16CMAGuqwO2lX1mTyyRRc=
golang.org/x/sys v0.0.0-20220422013727-9388b58f7150/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.7 h1:olpwvP2KacW1ZWvsR7uQhoyTYvKAupfQrRGBFM352Gk=
golang.org/x/time v0.0.0-20210723032227-1f47c861a9ac h1:7zkz7BUtwNFFqcowJ+RIgu2MaV/MapERkDIy+mwPyjs=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY=
golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE=
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc=
google.golang.org/genproto v0.0.0-20200513103714-09dca8ec2884/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c=
google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo=
google.golang.org/genproto v0.0.0-20211208223120-3a66f561d7aa h1:I0YcKz0I7OAhddo7ya8kMnvprhcWM045PmkBdMO9zN0=
google.golang.org/genproto v0.0.0-20211208223120-3a66f561d7aa/go.mod h1:5CzLGKJ67TSI2B9POpiiyGha0AjJvZIUgRMt1dSmuhc=
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg=
google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY=
google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk=
google.golang.org/grpc v1.33.1/go.mod h1:fr5YgcSWrqhRRxogOsw7RzIpsmvOZ6IcH4kBYTpR3n0=
google.golang.org/grpc v1.36.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU=
google.golang.org/grpc v1.40.0/go.mod h1:ogyxbiOoUXAkP+4+xa6PZSE9DZgIHtSpzjDTB9KAK34=
google.golang.org/grpc v1.46.0 h1:oCjezcn6g6A75TGoKYBPgKmVBLexhYLM6MebdrPApP8=
google.golang.org/grpc v1.46.0/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk=
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE=
google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo=
google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c=
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
google.golang.org/protobuf v1.27.1 h1:SnqbnDw1V7RiZcXPx5MEeqPv2s79L9i7BJUlG/+RurQ=
google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.3/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo=
gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo=
gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw=
honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=

View File

@@ -1,5 +1,5 @@
/* /*
© Copyright IBM Corporation 2018, 2022 © Copyright IBM Corporation 2018, 2023
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.
@@ -51,6 +51,7 @@ class JMSTests {
private static final Logger LOGGER = Logger.getLogger(JMSTests.class.getName()); private static final Logger LOGGER = Logger.getLogger(JMSTests.class.getName());
protected static final String ADDR = System.getenv("MQ_PORT_1414_TCP_ADDR"); protected static final String ADDR = System.getenv("MQ_PORT_1414_TCP_ADDR");
protected static final String USER = System.getenv("MQ_USERNAME"); protected static final String USER = System.getenv("MQ_USERNAME");
protected static final String PORT = System.getenv().getOrDefault("MQ_PORT_1414_OVERRIDE", "1414");
protected static final String PASSWORD = System.getenv("MQ_PASSWORD"); protected static final String PASSWORD = System.getenv("MQ_PASSWORD");
protected static final String CHANNEL = System.getenv("MQ_CHANNEL"); protected static final String CHANNEL = System.getenv("MQ_CHANNEL");
protected static final String TRUSTSTORE = System.getenv("MQ_TLS_TRUSTSTORE"); protected static final String TRUSTSTORE = System.getenv("MQ_TLS_TRUSTSTORE");
@@ -67,11 +68,11 @@ class JMSTests {
return ctx.getSocketFactory(); return ctx.getSocketFactory();
} }
static MQConnectionFactory createMQConnectionFactory(String channel, String addr) throws JMSException, IOException, GeneralSecurityException { static MQConnectionFactory createMQConnectionFactory(String channel, String addr, String port) throws JMSException, IOException, GeneralSecurityException {
MQConnectionFactory factory = new MQConnectionFactory(); MQConnectionFactory factory = new MQConnectionFactory();
factory.setTransportType(WMQConstants.WMQ_CM_CLIENT); factory.setTransportType(WMQConstants.WMQ_CM_CLIENT);
factory.setChannel(channel); factory.setChannel(channel);
factory.setConnectionNameList(String.format("%s(1414)", addr)); factory.setConnectionNameList(String.format("%s(%s)", addr, port));
if (TRUSTSTORE == null) { if (TRUSTSTORE == null) {
LOGGER.info("Not using TLS"); LOGGER.info("Not using TLS");
} }
@@ -93,9 +94,9 @@ class JMSTests {
/** /**
* Create a JMSContext with the supplied user and password. * Create a JMSContext with the supplied user and password.
*/ */
static JMSContext create(String channel, String addr, String user, String password) throws JMSException, IOException, GeneralSecurityException { static JMSContext create(String channel, String addr, String port, String user, String password) throws JMSException, IOException, GeneralSecurityException {
LOGGER.info(String.format("Connecting to %s/TCP/%s(1414) as %s", channel, addr, user)); LOGGER.info(String.format("Connecting to %s/TCP/%s(%s) as %s", channel, addr, port, user));
MQConnectionFactory factory = createMQConnectionFactory(channel, addr); MQConnectionFactory factory = createMQConnectionFactory(channel, addr, port);
// If a password is set, make sure it gets sent to the queue manager for authentication // If a password is set, make sure it gets sent to the queue manager for authentication
if (password != null) { if (password != null) {
factory.setBooleanProperty(WMQConstants.USER_AUTHENTICATION_MQCSP, true); factory.setBooleanProperty(WMQConstants.USER_AUTHENTICATION_MQCSP, true);
@@ -107,9 +108,9 @@ class JMSTests {
/** /**
* Create a JMSContext with the default user identity (from the OS) * Create a JMSContext with the default user identity (from the OS)
*/ */
static JMSContext create(String channel, String addr) throws JMSException, IOException, GeneralSecurityException { static JMSContext create(String channel, String addr, String port) throws JMSException, IOException, GeneralSecurityException {
LOGGER.info(String.format("Connecting to %s/TCP/%s(1414) as OS user '%s'", channel, addr, System.getProperty("user.name"))); LOGGER.info(String.format("Connecting to %s/TCP/%s(%s) as OS user '%s'", channel, addr, port, System.getProperty("user.name")));
MQConnectionFactory factory = createMQConnectionFactory(channel, addr); MQConnectionFactory factory = createMQConnectionFactory(channel, addr, port);
LOGGER.info(String.format("CSP authentication: %s", factory.getBooleanProperty(WMQConstants.USER_AUTHENTICATION_MQCSP))); LOGGER.info(String.format("CSP authentication: %s", factory.getBooleanProperty(WMQConstants.USER_AUTHENTICATION_MQCSP)));
return factory.createContext(); return factory.createContext();
} }
@@ -118,7 +119,7 @@ class JMSTests {
private static void waitForQueueManager() { private static void waitForQueueManager() {
for (int i = 0; i < 20; i++) { for (int i = 0; i < 20; i++) {
try { try {
Socket s = new Socket(ADDR, 1414); Socket s = new Socket(ADDR, Integer.parseInt(PORT));
s.close(); s.close();
return; return;
} catch (IOException e) { } catch (IOException e) {
@@ -132,7 +133,7 @@ class JMSTests {
@Test @Test
void putGetTest(TestInfo t) throws Exception { void putGetTest(TestInfo t) throws Exception {
context = create(CHANNEL, ADDR, USER, PASSWORD); context = create(CHANNEL, ADDR, PORT, USER, PASSWORD);
Queue queue = new MQQueue("DEV.QUEUE.1"); Queue queue = new MQQueue("DEV.QUEUE.1");
context.createProducer().send(queue, t.getDisplayName()); context.createProducer().send(queue, t.getDisplayName());
Message m = context.createConsumer(queue).receive(); Message m = context.createConsumer(queue).receive();
@@ -144,7 +145,7 @@ class JMSTests {
LOGGER.info(String.format("Password='%s'", PASSWORD)); LOGGER.info(String.format("Password='%s'", PASSWORD));
try { try {
// Don't pass a user/password, which should cause the default identity to be used // Don't pass a user/password, which should cause the default identity to be used
context = create(CHANNEL, ADDR); context = create(CHANNEL, ADDR, PORT);
} catch (DetailedJMSSecurityRuntimeException ex) { } catch (DetailedJMSSecurityRuntimeException ex) {
Throwable cause = ex.getCause(); Throwable cause = ex.getCause();
assertNotNull(cause); assertNotNull(cause);

View File

@@ -13,6 +13,7 @@ import (
"strings" "strings"
"sync" "sync"
"google.golang.org/protobuf/reflect/protodesc"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
"google.golang.org/protobuf/runtime/protoimpl" "google.golang.org/protobuf/runtime/protoimpl"
@@ -62,14 +63,7 @@ func FileDescriptor(s filePath) fileDescGZIP {
// Find the descriptor in the v2 registry. // Find the descriptor in the v2 registry.
var b []byte var b []byte
if fd, _ := protoregistry.GlobalFiles.FindFileByPath(s); fd != nil { if fd, _ := protoregistry.GlobalFiles.FindFileByPath(s); fd != nil {
if fd, ok := fd.(interface{ ProtoLegacyRawDesc() []byte }); ok { b, _ = Marshal(protodesc.ToFileDescriptorProto(fd))
b = fd.ProtoLegacyRawDesc()
} else {
// TODO: Use protodesc.ToFileDescriptorProto to construct
// a descriptorpb.FileDescriptorProto and marshal it.
// However, doing so causes the proto package to have a dependency
// on descriptorpb, leading to cyclic dependency issues.
}
} }
// Locally cache the raw descriptor form for the file. // Locally cache the raw descriptor form for the file.

View File

@@ -19,6 +19,8 @@ const urlPrefix = "type.googleapis.com/"
// AnyMessageName returns the message name contained in an anypb.Any message. // AnyMessageName returns the message name contained in an anypb.Any message.
// Most type assertions should use the Is function instead. // Most type assertions should use the Is function instead.
//
// Deprecated: Call the any.MessageName method instead.
func AnyMessageName(any *anypb.Any) (string, error) { func AnyMessageName(any *anypb.Any) (string, error) {
name, err := anyMessageName(any) name, err := anyMessageName(any)
return string(name), err return string(name), err
@@ -38,6 +40,8 @@ func anyMessageName(any *anypb.Any) (protoreflect.FullName, error) {
} }
// MarshalAny marshals the given message m into an anypb.Any message. // MarshalAny marshals the given message m into an anypb.Any message.
//
// Deprecated: Call the anypb.New function instead.
func MarshalAny(m proto.Message) (*anypb.Any, error) { func MarshalAny(m proto.Message) (*anypb.Any, error) {
switch dm := m.(type) { switch dm := m.(type) {
case DynamicAny: case DynamicAny:
@@ -58,6 +62,9 @@ func MarshalAny(m proto.Message) (*anypb.Any, error) {
// Empty returns a new message of the type specified in an anypb.Any message. // Empty returns a new message of the type specified in an anypb.Any message.
// It returns protoregistry.NotFound if the corresponding message type could not // It returns protoregistry.NotFound if the corresponding message type could not
// be resolved in the global registry. // be resolved in the global registry.
//
// Deprecated: Use protoregistry.GlobalTypes.FindMessageByName instead
// to resolve the message name and create a new instance of it.
func Empty(any *anypb.Any) (proto.Message, error) { func Empty(any *anypb.Any) (proto.Message, error) {
name, err := anyMessageName(any) name, err := anyMessageName(any)
if err != nil { if err != nil {
@@ -76,6 +83,8 @@ func Empty(any *anypb.Any) (proto.Message, error) {
// //
// The target message m may be a *DynamicAny message. If the underlying message // The target message m may be a *DynamicAny message. If the underlying message
// type could not be resolved, then this returns protoregistry.NotFound. // type could not be resolved, then this returns protoregistry.NotFound.
//
// Deprecated: Call the any.UnmarshalTo method instead.
func UnmarshalAny(any *anypb.Any, m proto.Message) error { func UnmarshalAny(any *anypb.Any, m proto.Message) error {
if dm, ok := m.(*DynamicAny); ok { if dm, ok := m.(*DynamicAny); ok {
if dm.Message == nil { if dm.Message == nil {
@@ -100,6 +109,8 @@ func UnmarshalAny(any *anypb.Any, m proto.Message) error {
} }
// Is reports whether the Any message contains a message of the specified type. // Is reports whether the Any message contains a message of the specified type.
//
// Deprecated: Call the any.MessageIs method instead.
func Is(any *anypb.Any, m proto.Message) bool { func Is(any *anypb.Any, m proto.Message) bool {
if any == nil || m == nil { if any == nil || m == nil {
return false return false
@@ -119,6 +130,9 @@ func Is(any *anypb.Any, m proto.Message) bool {
// var x ptypes.DynamicAny // var x ptypes.DynamicAny
// if err := ptypes.UnmarshalAny(a, &x); err != nil { ... } // if err := ptypes.UnmarshalAny(a, &x); err != nil { ... }
// fmt.Printf("unmarshaled message: %v", x.Message) // fmt.Printf("unmarshaled message: %v", x.Message)
//
// Deprecated: Use the any.UnmarshalNew method instead to unmarshal
// the any message contents into a new instance of the underlying message.
type DynamicAny struct{ proto.Message } type DynamicAny struct{ proto.Message }
func (m DynamicAny) String() string { func (m DynamicAny) String() string {

View File

@@ -3,4 +3,8 @@
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
// Package ptypes provides functionality for interacting with well-known types. // Package ptypes provides functionality for interacting with well-known types.
//
// Deprecated: Well-known types have specialized functionality directly
// injected into the generated packages for each message type.
// See the deprecation notice for each function for the suggested alternative.
package ptypes package ptypes

View File

@@ -21,6 +21,8 @@ const (
// Duration converts a durationpb.Duration to a time.Duration. // Duration converts a durationpb.Duration to a time.Duration.
// Duration returns an error if dur is invalid or overflows a time.Duration. // Duration returns an error if dur is invalid or overflows a time.Duration.
//
// Deprecated: Call the dur.AsDuration and dur.CheckValid methods instead.
func Duration(dur *durationpb.Duration) (time.Duration, error) { func Duration(dur *durationpb.Duration) (time.Duration, error) {
if err := validateDuration(dur); err != nil { if err := validateDuration(dur); err != nil {
return 0, err return 0, err
@@ -39,6 +41,8 @@ func Duration(dur *durationpb.Duration) (time.Duration, error) {
} }
// DurationProto converts a time.Duration to a durationpb.Duration. // DurationProto converts a time.Duration to a durationpb.Duration.
//
// Deprecated: Call the durationpb.New function instead.
func DurationProto(d time.Duration) *durationpb.Duration { func DurationProto(d time.Duration) *durationpb.Duration {
nanos := d.Nanoseconds() nanos := d.Nanoseconds()
secs := nanos / 1e9 secs := nanos / 1e9

View File

@@ -33,6 +33,8 @@ const (
// //
// A nil Timestamp returns an error. The first return value in that case is // A nil Timestamp returns an error. The first return value in that case is
// undefined. // undefined.
//
// Deprecated: Call the ts.AsTime and ts.CheckValid methods instead.
func Timestamp(ts *timestamppb.Timestamp) (time.Time, error) { func Timestamp(ts *timestamppb.Timestamp) (time.Time, error) {
// Don't return the zero value on error, because corresponds to a valid // Don't return the zero value on error, because corresponds to a valid
// timestamp. Instead return whatever time.Unix gives us. // timestamp. Instead return whatever time.Unix gives us.
@@ -46,6 +48,8 @@ func Timestamp(ts *timestamppb.Timestamp) (time.Time, error) {
} }
// TimestampNow returns a google.protobuf.Timestamp for the current time. // TimestampNow returns a google.protobuf.Timestamp for the current time.
//
// Deprecated: Call the timestamppb.Now function instead.
func TimestampNow() *timestamppb.Timestamp { func TimestampNow() *timestamppb.Timestamp {
ts, err := TimestampProto(time.Now()) ts, err := TimestampProto(time.Now())
if err != nil { if err != nil {
@@ -56,6 +60,8 @@ func TimestampNow() *timestamppb.Timestamp {
// TimestampProto converts the time.Time to a google.protobuf.Timestamp proto. // TimestampProto converts the time.Time to a google.protobuf.Timestamp proto.
// It returns an error if the resulting Timestamp is invalid. // It returns an error if the resulting Timestamp is invalid.
//
// Deprecated: Call the timestamppb.New function instead.
func TimestampProto(t time.Time) (*timestamppb.Timestamp, error) { func TimestampProto(t time.Time) (*timestamppb.Timestamp, error) {
ts := &timestamppb.Timestamp{ ts := &timestamppb.Timestamp{
Seconds: t.Unix(), Seconds: t.Unix(),
@@ -69,6 +75,9 @@ func TimestampProto(t time.Time) (*timestamppb.Timestamp, error) {
// TimestampString returns the RFC 3339 string for valid Timestamps. // TimestampString returns the RFC 3339 string for valid Timestamps.
// For invalid Timestamps, it returns an error message in parentheses. // For invalid Timestamps, it returns an error message in parentheses.
//
// Deprecated: Call the ts.AsTime method instead,
// followed by a call to the Format method on the time.Time value.
func TimestampString(ts *timestamppb.Timestamp) string { func TimestampString(ts *timestamppb.Timestamp) string {
t, err := Timestamp(ts) t, err := Timestamp(ts)
if err != nil { if err != nil {

File diff suppressed because it is too large Load Diff

View File

@@ -1,3 +0,0 @@
# This source code refers to The Go Authors for copyright purposes.
# The master list of authors is in the main Go distribution,
# visible at https://tip.golang.org/AUTHORS.

View File

@@ -1,3 +0,0 @@
# This source code was written by the Go contributors.
# The master list of contributors is in the main Go distribution,
# visible at https://tip.golang.org/CONTRIBUTORS.

View File

@@ -17,11 +17,11 @@ import (
"google.golang.org/protobuf/internal/set" "google.golang.org/protobuf/internal/set"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
) )
// Unmarshal reads the given []byte into the given proto.Message. // Unmarshal reads the given []byte into the given [proto.Message].
// The provided message must be mutable (e.g., a non-nil pointer to a message). // The provided message must be mutable (e.g., a non-nil pointer to a message).
func Unmarshal(b []byte, m proto.Message) error { func Unmarshal(b []byte, m proto.Message) error {
return UnmarshalOptions{}.Unmarshal(b, m) return UnmarshalOptions{}.Unmarshal(b, m)
@@ -51,7 +51,7 @@ type UnmarshalOptions struct {
} }
} }
// Unmarshal reads the given []byte and populates the given proto.Message // Unmarshal reads the given []byte and populates the given [proto.Message]
// using options in the UnmarshalOptions object. // using options in the UnmarshalOptions object.
// The provided message must be mutable (e.g., a non-nil pointer to a message). // The provided message must be mutable (e.g., a non-nil pointer to a message).
func (o UnmarshalOptions) Unmarshal(b []byte, m proto.Message) error { func (o UnmarshalOptions) Unmarshal(b []byte, m proto.Message) error {
@@ -103,7 +103,7 @@ func (d decoder) syntaxError(pos int, f string, x ...interface{}) error {
} }
// unmarshalMessage unmarshals into the given protoreflect.Message. // unmarshalMessage unmarshals into the given protoreflect.Message.
func (d decoder) unmarshalMessage(m pref.Message, checkDelims bool) error { func (d decoder) unmarshalMessage(m protoreflect.Message, checkDelims bool) error {
messageDesc := m.Descriptor() messageDesc := m.Descriptor()
if !flags.ProtoLegacy && messageset.IsMessageSet(messageDesc) { if !flags.ProtoLegacy && messageset.IsMessageSet(messageDesc) {
return errors.New("no support for proto1 MessageSets") return errors.New("no support for proto1 MessageSets")
@@ -150,24 +150,24 @@ func (d decoder) unmarshalMessage(m pref.Message, checkDelims bool) error {
} }
// Resolve the field descriptor. // Resolve the field descriptor.
var name pref.Name var name protoreflect.Name
var fd pref.FieldDescriptor var fd protoreflect.FieldDescriptor
var xt pref.ExtensionType var xt protoreflect.ExtensionType
var xtErr error var xtErr error
var isFieldNumberName bool var isFieldNumberName bool
switch tok.NameKind() { switch tok.NameKind() {
case text.IdentName: case text.IdentName:
name = pref.Name(tok.IdentName()) name = protoreflect.Name(tok.IdentName())
fd = fieldDescs.ByTextName(string(name)) fd = fieldDescs.ByTextName(string(name))
case text.TypeName: case text.TypeName:
// Handle extensions only. This code path is not for Any. // Handle extensions only. This code path is not for Any.
xt, xtErr = d.opts.Resolver.FindExtensionByName(pref.FullName(tok.TypeName())) xt, xtErr = d.opts.Resolver.FindExtensionByName(protoreflect.FullName(tok.TypeName()))
case text.FieldNumber: case text.FieldNumber:
isFieldNumberName = true isFieldNumberName = true
num := pref.FieldNumber(tok.FieldNumber()) num := protoreflect.FieldNumber(tok.FieldNumber())
if !num.IsValid() { if !num.IsValid() {
return d.newError(tok.Pos(), "invalid field number: %d", num) return d.newError(tok.Pos(), "invalid field number: %d", num)
} }
@@ -215,7 +215,7 @@ func (d decoder) unmarshalMessage(m pref.Message, checkDelims bool) error {
switch { switch {
case fd.IsList(): case fd.IsList():
kind := fd.Kind() kind := fd.Kind()
if kind != pref.MessageKind && kind != pref.GroupKind && !tok.HasSeparator() { if kind != protoreflect.MessageKind && kind != protoreflect.GroupKind && !tok.HasSeparator() {
return d.syntaxError(tok.Pos(), "missing field separator :") return d.syntaxError(tok.Pos(), "missing field separator :")
} }
@@ -232,7 +232,7 @@ func (d decoder) unmarshalMessage(m pref.Message, checkDelims bool) error {
default: default:
kind := fd.Kind() kind := fd.Kind()
if kind != pref.MessageKind && kind != pref.GroupKind && !tok.HasSeparator() { if kind != protoreflect.MessageKind && kind != protoreflect.GroupKind && !tok.HasSeparator() {
return d.syntaxError(tok.Pos(), "missing field separator :") return d.syntaxError(tok.Pos(), "missing field separator :")
} }
@@ -262,11 +262,11 @@ func (d decoder) unmarshalMessage(m pref.Message, checkDelims bool) error {
// unmarshalSingular unmarshals a non-repeated field value specified by the // unmarshalSingular unmarshals a non-repeated field value specified by the
// given FieldDescriptor. // given FieldDescriptor.
func (d decoder) unmarshalSingular(fd pref.FieldDescriptor, m pref.Message) error { func (d decoder) unmarshalSingular(fd protoreflect.FieldDescriptor, m protoreflect.Message) error {
var val pref.Value var val protoreflect.Value
var err error var err error
switch fd.Kind() { switch fd.Kind() {
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
val = m.NewField(fd) val = m.NewField(fd)
err = d.unmarshalMessage(val.Message(), true) err = d.unmarshalMessage(val.Message(), true)
default: default:
@@ -280,94 +280,94 @@ func (d decoder) unmarshalSingular(fd pref.FieldDescriptor, m pref.Message) erro
// unmarshalScalar unmarshals a scalar/enum protoreflect.Value specified by the // unmarshalScalar unmarshals a scalar/enum protoreflect.Value specified by the
// given FieldDescriptor. // given FieldDescriptor.
func (d decoder) unmarshalScalar(fd pref.FieldDescriptor) (pref.Value, error) { func (d decoder) unmarshalScalar(fd protoreflect.FieldDescriptor) (protoreflect.Value, error) {
tok, err := d.Read() tok, err := d.Read()
if err != nil { if err != nil {
return pref.Value{}, err return protoreflect.Value{}, err
} }
if tok.Kind() != text.Scalar { if tok.Kind() != text.Scalar {
return pref.Value{}, d.unexpectedTokenError(tok) return protoreflect.Value{}, d.unexpectedTokenError(tok)
} }
kind := fd.Kind() kind := fd.Kind()
switch kind { switch kind {
case pref.BoolKind: case protoreflect.BoolKind:
if b, ok := tok.Bool(); ok { if b, ok := tok.Bool(); ok {
return pref.ValueOfBool(b), nil return protoreflect.ValueOfBool(b), nil
} }
case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind: case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind:
if n, ok := tok.Int32(); ok { if n, ok := tok.Int32(); ok {
return pref.ValueOfInt32(n), nil return protoreflect.ValueOfInt32(n), nil
} }
case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind: case protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
if n, ok := tok.Int64(); ok { if n, ok := tok.Int64(); ok {
return pref.ValueOfInt64(n), nil return protoreflect.ValueOfInt64(n), nil
} }
case pref.Uint32Kind, pref.Fixed32Kind: case protoreflect.Uint32Kind, protoreflect.Fixed32Kind:
if n, ok := tok.Uint32(); ok { if n, ok := tok.Uint32(); ok {
return pref.ValueOfUint32(n), nil return protoreflect.ValueOfUint32(n), nil
} }
case pref.Uint64Kind, pref.Fixed64Kind: case protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
if n, ok := tok.Uint64(); ok { if n, ok := tok.Uint64(); ok {
return pref.ValueOfUint64(n), nil return protoreflect.ValueOfUint64(n), nil
} }
case pref.FloatKind: case protoreflect.FloatKind:
if n, ok := tok.Float32(); ok { if n, ok := tok.Float32(); ok {
return pref.ValueOfFloat32(n), nil return protoreflect.ValueOfFloat32(n), nil
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if n, ok := tok.Float64(); ok { if n, ok := tok.Float64(); ok {
return pref.ValueOfFloat64(n), nil return protoreflect.ValueOfFloat64(n), nil
} }
case pref.StringKind: case protoreflect.StringKind:
if s, ok := tok.String(); ok { if s, ok := tok.String(); ok {
if strs.EnforceUTF8(fd) && !utf8.ValidString(s) { if strs.EnforceUTF8(fd) && !utf8.ValidString(s) {
return pref.Value{}, d.newError(tok.Pos(), "contains invalid UTF-8") return protoreflect.Value{}, d.newError(tok.Pos(), "contains invalid UTF-8")
} }
return pref.ValueOfString(s), nil return protoreflect.ValueOfString(s), nil
} }
case pref.BytesKind: case protoreflect.BytesKind:
if b, ok := tok.String(); ok { if b, ok := tok.String(); ok {
return pref.ValueOfBytes([]byte(b)), nil return protoreflect.ValueOfBytes([]byte(b)), nil
} }
case pref.EnumKind: case protoreflect.EnumKind:
if lit, ok := tok.Enum(); ok { if lit, ok := tok.Enum(); ok {
// Lookup EnumNumber based on name. // Lookup EnumNumber based on name.
if enumVal := fd.Enum().Values().ByName(pref.Name(lit)); enumVal != nil { if enumVal := fd.Enum().Values().ByName(protoreflect.Name(lit)); enumVal != nil {
return pref.ValueOfEnum(enumVal.Number()), nil return protoreflect.ValueOfEnum(enumVal.Number()), nil
} }
} }
if num, ok := tok.Int32(); ok { if num, ok := tok.Int32(); ok {
return pref.ValueOfEnum(pref.EnumNumber(num)), nil return protoreflect.ValueOfEnum(protoreflect.EnumNumber(num)), nil
} }
default: default:
panic(fmt.Sprintf("invalid scalar kind %v", kind)) panic(fmt.Sprintf("invalid scalar kind %v", kind))
} }
return pref.Value{}, d.newError(tok.Pos(), "invalid value for %v type: %v", kind, tok.RawString()) return protoreflect.Value{}, d.newError(tok.Pos(), "invalid value for %v type: %v", kind, tok.RawString())
} }
// unmarshalList unmarshals into given protoreflect.List. A list value can // unmarshalList unmarshals into given protoreflect.List. A list value can
// either be in [] syntax or simply just a single scalar/message value. // either be in [] syntax or simply just a single scalar/message value.
func (d decoder) unmarshalList(fd pref.FieldDescriptor, list pref.List) error { func (d decoder) unmarshalList(fd protoreflect.FieldDescriptor, list protoreflect.List) error {
tok, err := d.Peek() tok, err := d.Peek()
if err != nil { if err != nil {
return err return err
} }
switch fd.Kind() { switch fd.Kind() {
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
switch tok.Kind() { switch tok.Kind() {
case text.ListOpen: case text.ListOpen:
d.Read() d.Read()
@@ -441,22 +441,22 @@ func (d decoder) unmarshalList(fd pref.FieldDescriptor, list pref.List) error {
// unmarshalMap unmarshals into given protoreflect.Map. A map value is a // unmarshalMap unmarshals into given protoreflect.Map. A map value is a
// textproto message containing {key: <kvalue>, value: <mvalue>}. // textproto message containing {key: <kvalue>, value: <mvalue>}.
func (d decoder) unmarshalMap(fd pref.FieldDescriptor, mmap pref.Map) error { func (d decoder) unmarshalMap(fd protoreflect.FieldDescriptor, mmap protoreflect.Map) error {
// Determine ahead whether map entry is a scalar type or a message type in // Determine ahead whether map entry is a scalar type or a message type in
// order to call the appropriate unmarshalMapValue func inside // order to call the appropriate unmarshalMapValue func inside
// unmarshalMapEntry. // unmarshalMapEntry.
var unmarshalMapValue func() (pref.Value, error) var unmarshalMapValue func() (protoreflect.Value, error)
switch fd.MapValue().Kind() { switch fd.MapValue().Kind() {
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
unmarshalMapValue = func() (pref.Value, error) { unmarshalMapValue = func() (protoreflect.Value, error) {
pval := mmap.NewValue() pval := mmap.NewValue()
if err := d.unmarshalMessage(pval.Message(), true); err != nil { if err := d.unmarshalMessage(pval.Message(), true); err != nil {
return pref.Value{}, err return protoreflect.Value{}, err
} }
return pval, nil return pval, nil
} }
default: default:
unmarshalMapValue = func() (pref.Value, error) { unmarshalMapValue = func() (protoreflect.Value, error) {
return d.unmarshalScalar(fd.MapValue()) return d.unmarshalScalar(fd.MapValue())
} }
} }
@@ -494,9 +494,9 @@ func (d decoder) unmarshalMap(fd pref.FieldDescriptor, mmap pref.Map) error {
// unmarshalMap unmarshals into given protoreflect.Map. A map value is a // unmarshalMap unmarshals into given protoreflect.Map. A map value is a
// textproto message containing {key: <kvalue>, value: <mvalue>}. // textproto message containing {key: <kvalue>, value: <mvalue>}.
func (d decoder) unmarshalMapEntry(fd pref.FieldDescriptor, mmap pref.Map, unmarshalMapValue func() (pref.Value, error)) error { func (d decoder) unmarshalMapEntry(fd protoreflect.FieldDescriptor, mmap protoreflect.Map, unmarshalMapValue func() (protoreflect.Value, error)) error {
var key pref.MapKey var key protoreflect.MapKey
var pval pref.Value var pval protoreflect.Value
Loop: Loop:
for { for {
// Read field name. // Read field name.
@@ -520,7 +520,7 @@ Loop:
return d.unexpectedTokenError(tok) return d.unexpectedTokenError(tok)
} }
switch name := pref.Name(tok.IdentName()); name { switch name := protoreflect.Name(tok.IdentName()); name {
case genid.MapEntry_Key_field_name: case genid.MapEntry_Key_field_name:
if !tok.HasSeparator() { if !tok.HasSeparator() {
return d.syntaxError(tok.Pos(), "missing field separator :") return d.syntaxError(tok.Pos(), "missing field separator :")
@@ -535,7 +535,7 @@ Loop:
key = val.MapKey() key = val.MapKey()
case genid.MapEntry_Value_field_name: case genid.MapEntry_Value_field_name:
if kind := fd.MapValue().Kind(); (kind != pref.MessageKind) && (kind != pref.GroupKind) { if kind := fd.MapValue().Kind(); (kind != protoreflect.MessageKind) && (kind != protoreflect.GroupKind) {
if !tok.HasSeparator() { if !tok.HasSeparator() {
return d.syntaxError(tok.Pos(), "missing field separator :") return d.syntaxError(tok.Pos(), "missing field separator :")
} }
@@ -561,7 +561,7 @@ Loop:
} }
if !pval.IsValid() { if !pval.IsValid() {
switch fd.MapValue().Kind() { switch fd.MapValue().Kind() {
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
// If value field is not set for message/group types, construct an // If value field is not set for message/group types, construct an
// empty one as default. // empty one as default.
pval = mmap.NewValue() pval = mmap.NewValue()
@@ -575,7 +575,7 @@ Loop:
// unmarshalAny unmarshals an Any textproto. It can either be in expanded form // unmarshalAny unmarshals an Any textproto. It can either be in expanded form
// or non-expanded form. // or non-expanded form.
func (d decoder) unmarshalAny(m pref.Message, checkDelims bool) error { func (d decoder) unmarshalAny(m protoreflect.Message, checkDelims bool) error {
var typeURL string var typeURL string
var bValue []byte var bValue []byte
var seenTypeUrl bool var seenTypeUrl bool
@@ -619,7 +619,7 @@ Loop:
return d.syntaxError(tok.Pos(), "missing field separator :") return d.syntaxError(tok.Pos(), "missing field separator :")
} }
switch name := pref.Name(tok.IdentName()); name { switch name := protoreflect.Name(tok.IdentName()); name {
case genid.Any_TypeUrl_field_name: case genid.Any_TypeUrl_field_name:
if seenTypeUrl { if seenTypeUrl {
return d.newError(tok.Pos(), "duplicate %v field", genid.Any_TypeUrl_field_fullname) return d.newError(tok.Pos(), "duplicate %v field", genid.Any_TypeUrl_field_fullname)
@@ -686,10 +686,10 @@ Loop:
fds := m.Descriptor().Fields() fds := m.Descriptor().Fields()
if len(typeURL) > 0 { if len(typeURL) > 0 {
m.Set(fds.ByNumber(genid.Any_TypeUrl_field_number), pref.ValueOfString(typeURL)) m.Set(fds.ByNumber(genid.Any_TypeUrl_field_number), protoreflect.ValueOfString(typeURL))
} }
if len(bValue) > 0 { if len(bValue) > 0 {
m.Set(fds.ByNumber(genid.Any_Value_field_number), pref.ValueOfBytes(bValue)) m.Set(fds.ByNumber(genid.Any_Value_field_number), protoreflect.ValueOfBytes(bValue))
} }
return nil return nil
} }
@@ -739,14 +739,13 @@ func (d decoder) skipValue() error {
case text.ListClose: case text.ListClose:
return nil return nil
case text.MessageOpen: case text.MessageOpen:
return d.skipMessageValue() if err := d.skipMessageValue(); err != nil {
return err
}
default: default:
// Skip items. This will not validate whether skipped values are // Skip items. This will not validate whether skipped values are
// of the same type or not, same behavior as C++ // of the same type or not, same behavior as C++
// TextFormat::Parser::AllowUnknownField(true) version 3.8.0. // TextFormat::Parser::AllowUnknownField(true) version 3.8.0.
if err := d.skipValue(); err != nil {
return err
}
} }
} }
} }

View File

@@ -20,7 +20,6 @@ import (
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
pref "google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
) )
@@ -34,7 +33,7 @@ func Format(m proto.Message) string {
return MarshalOptions{Multiline: true}.Format(m) return MarshalOptions{Multiline: true}.Format(m)
} }
// Marshal writes the given proto.Message in textproto format using default // Marshal writes the given [proto.Message] in textproto format using default
// options. Do not depend on the output being stable. It may change over time // options. Do not depend on the output being stable. It may change over time
// across different versions of the program. // across different versions of the program.
func Marshal(m proto.Message) ([]byte, error) { func Marshal(m proto.Message) ([]byte, error) {
@@ -98,17 +97,23 @@ func (o MarshalOptions) Format(m proto.Message) string {
return string(b) return string(b)
} }
// Marshal writes the given proto.Message in textproto format using options in // Marshal writes the given [proto.Message] in textproto format using options in
// MarshalOptions object. Do not depend on the output being stable. It may // MarshalOptions object. Do not depend on the output being stable. It may
// change over time across different versions of the program. // change over time across different versions of the program.
func (o MarshalOptions) Marshal(m proto.Message) ([]byte, error) { func (o MarshalOptions) Marshal(m proto.Message) ([]byte, error) {
return o.marshal(m) return o.marshal(nil, m)
}
// MarshalAppend appends the textproto format encoding of m to b,
// returning the result.
func (o MarshalOptions) MarshalAppend(b []byte, m proto.Message) ([]byte, error) {
return o.marshal(b, m)
} }
// marshal is a centralized function that all marshal operations go through. // marshal is a centralized function that all marshal operations go through.
// For profiling purposes, avoid changing the name of this function or // For profiling purposes, avoid changing the name of this function or
// introducing other code paths for marshal that do not go through this. // introducing other code paths for marshal that do not go through this.
func (o MarshalOptions) marshal(m proto.Message) ([]byte, error) { func (o MarshalOptions) marshal(b []byte, m proto.Message) ([]byte, error) {
var delims = [2]byte{'{', '}'} var delims = [2]byte{'{', '}'}
if o.Multiline && o.Indent == "" { if o.Multiline && o.Indent == "" {
@@ -118,7 +123,7 @@ func (o MarshalOptions) marshal(m proto.Message) ([]byte, error) {
o.Resolver = protoregistry.GlobalTypes o.Resolver = protoregistry.GlobalTypes
} }
internalEnc, err := text.NewEncoder(o.Indent, delims, o.EmitASCII) internalEnc, err := text.NewEncoder(b, o.Indent, delims, o.EmitASCII)
if err != nil { if err != nil {
return nil, err return nil, err
} }
@@ -126,7 +131,7 @@ func (o MarshalOptions) marshal(m proto.Message) ([]byte, error) {
// Treat nil message interface as an empty message, // Treat nil message interface as an empty message,
// in which case there is nothing to output. // in which case there is nothing to output.
if m == nil { if m == nil {
return []byte{}, nil return b, nil
} }
enc := encoder{internalEnc, o} enc := encoder{internalEnc, o}
@@ -150,7 +155,7 @@ type encoder struct {
} }
// marshalMessage marshals the given protoreflect.Message. // marshalMessage marshals the given protoreflect.Message.
func (e encoder) marshalMessage(m pref.Message, inclDelims bool) error { func (e encoder) marshalMessage(m protoreflect.Message, inclDelims bool) error {
messageDesc := m.Descriptor() messageDesc := m.Descriptor()
if !flags.ProtoLegacy && messageset.IsMessageSet(messageDesc) { if !flags.ProtoLegacy && messageset.IsMessageSet(messageDesc) {
return errors.New("no support for proto1 MessageSets") return errors.New("no support for proto1 MessageSets")
@@ -190,7 +195,7 @@ func (e encoder) marshalMessage(m pref.Message, inclDelims bool) error {
} }
// marshalField marshals the given field with protoreflect.Value. // marshalField marshals the given field with protoreflect.Value.
func (e encoder) marshalField(name string, val pref.Value, fd pref.FieldDescriptor) error { func (e encoder) marshalField(name string, val protoreflect.Value, fd protoreflect.FieldDescriptor) error {
switch { switch {
case fd.IsList(): case fd.IsList():
return e.marshalList(name, val.List(), fd) return e.marshalList(name, val.List(), fd)
@@ -204,40 +209,40 @@ func (e encoder) marshalField(name string, val pref.Value, fd pref.FieldDescript
// marshalSingular marshals the given non-repeated field value. This includes // marshalSingular marshals the given non-repeated field value. This includes
// all scalar types, enums, messages, and groups. // all scalar types, enums, messages, and groups.
func (e encoder) marshalSingular(val pref.Value, fd pref.FieldDescriptor) error { func (e encoder) marshalSingular(val protoreflect.Value, fd protoreflect.FieldDescriptor) error {
kind := fd.Kind() kind := fd.Kind()
switch kind { switch kind {
case pref.BoolKind: case protoreflect.BoolKind:
e.WriteBool(val.Bool()) e.WriteBool(val.Bool())
case pref.StringKind: case protoreflect.StringKind:
s := val.String() s := val.String()
if !e.opts.allowInvalidUTF8 && strs.EnforceUTF8(fd) && !utf8.ValidString(s) { if !e.opts.allowInvalidUTF8 && strs.EnforceUTF8(fd) && !utf8.ValidString(s) {
return errors.InvalidUTF8(string(fd.FullName())) return errors.InvalidUTF8(string(fd.FullName()))
} }
e.WriteString(s) e.WriteString(s)
case pref.Int32Kind, pref.Int64Kind, case protoreflect.Int32Kind, protoreflect.Int64Kind,
pref.Sint32Kind, pref.Sint64Kind, protoreflect.Sint32Kind, protoreflect.Sint64Kind,
pref.Sfixed32Kind, pref.Sfixed64Kind: protoreflect.Sfixed32Kind, protoreflect.Sfixed64Kind:
e.WriteInt(val.Int()) e.WriteInt(val.Int())
case pref.Uint32Kind, pref.Uint64Kind, case protoreflect.Uint32Kind, protoreflect.Uint64Kind,
pref.Fixed32Kind, pref.Fixed64Kind: protoreflect.Fixed32Kind, protoreflect.Fixed64Kind:
e.WriteUint(val.Uint()) e.WriteUint(val.Uint())
case pref.FloatKind: case protoreflect.FloatKind:
// Encoder.WriteFloat handles the special numbers NaN and infinites. // Encoder.WriteFloat handles the special numbers NaN and infinites.
e.WriteFloat(val.Float(), 32) e.WriteFloat(val.Float(), 32)
case pref.DoubleKind: case protoreflect.DoubleKind:
// Encoder.WriteFloat handles the special numbers NaN and infinites. // Encoder.WriteFloat handles the special numbers NaN and infinites.
e.WriteFloat(val.Float(), 64) e.WriteFloat(val.Float(), 64)
case pref.BytesKind: case protoreflect.BytesKind:
e.WriteString(string(val.Bytes())) e.WriteString(string(val.Bytes()))
case pref.EnumKind: case protoreflect.EnumKind:
num := val.Enum() num := val.Enum()
if desc := fd.Enum().Values().ByNumber(num); desc != nil { if desc := fd.Enum().Values().ByNumber(num); desc != nil {
e.WriteLiteral(string(desc.Name())) e.WriteLiteral(string(desc.Name()))
@@ -246,7 +251,7 @@ func (e encoder) marshalSingular(val pref.Value, fd pref.FieldDescriptor) error
e.WriteInt(int64(num)) e.WriteInt(int64(num))
} }
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
return e.marshalMessage(val.Message(), true) return e.marshalMessage(val.Message(), true)
default: default:
@@ -256,7 +261,7 @@ func (e encoder) marshalSingular(val pref.Value, fd pref.FieldDescriptor) error
} }
// marshalList marshals the given protoreflect.List as multiple name-value fields. // marshalList marshals the given protoreflect.List as multiple name-value fields.
func (e encoder) marshalList(name string, list pref.List, fd pref.FieldDescriptor) error { func (e encoder) marshalList(name string, list protoreflect.List, fd protoreflect.FieldDescriptor) error {
size := list.Len() size := list.Len()
for i := 0; i < size; i++ { for i := 0; i < size; i++ {
e.WriteName(name) e.WriteName(name)
@@ -268,9 +273,9 @@ func (e encoder) marshalList(name string, list pref.List, fd pref.FieldDescripto
} }
// marshalMap marshals the given protoreflect.Map as multiple name-value fields. // marshalMap marshals the given protoreflect.Map as multiple name-value fields.
func (e encoder) marshalMap(name string, mmap pref.Map, fd pref.FieldDescriptor) error { func (e encoder) marshalMap(name string, mmap protoreflect.Map, fd protoreflect.FieldDescriptor) error {
var err error var err error
order.RangeEntries(mmap, order.GenericKeyOrder, func(key pref.MapKey, val pref.Value) bool { order.RangeEntries(mmap, order.GenericKeyOrder, func(key protoreflect.MapKey, val protoreflect.Value) bool {
e.WriteName(name) e.WriteName(name)
e.StartMessage() e.StartMessage()
defer e.EndMessage() defer e.EndMessage()
@@ -334,7 +339,7 @@ func (e encoder) marshalUnknown(b []byte) {
// marshalAny marshals the given google.protobuf.Any message in expanded form. // marshalAny marshals the given google.protobuf.Any message in expanded form.
// It returns true if it was able to marshal, else false. // It returns true if it was able to marshal, else false.
func (e encoder) marshalAny(any pref.Message) bool { func (e encoder) marshalAny(any protoreflect.Message) bool {
// Construct the embedded message. // Construct the embedded message.
fds := any.Descriptor().Fields() fds := any.Descriptor().Fields()
fdType := fds.ByNumber(genid.Any_TypeUrl_field_number) fdType := fds.ByNumber(genid.Any_TypeUrl_field_number)

View File

@@ -3,10 +3,10 @@
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
// Package protowire parses and formats the raw wire encoding. // Package protowire parses and formats the raw wire encoding.
// See https://developers.google.com/protocol-buffers/docs/encoding. // See https://protobuf.dev/programming-guides/encoding.
// //
// For marshaling and unmarshaling entire protobuf messages, // For marshaling and unmarshaling entire protobuf messages,
// use the "google.golang.org/protobuf/proto" package instead. // use the [google.golang.org/protobuf/proto] package instead.
package protowire package protowire
import ( import (
@@ -25,15 +25,12 @@ const (
FirstReservedNumber Number = 19000 FirstReservedNumber Number = 19000
LastReservedNumber Number = 19999 LastReservedNumber Number = 19999
MaxValidNumber Number = 1<<29 - 1 MaxValidNumber Number = 1<<29 - 1
DefaultRecursionLimit = 10000
) )
// IsValid reports whether the field number is semantically valid. // IsValid reports whether the field number is semantically valid.
//
// Note that while numbers within the reserved range are semantically invalid,
// they are syntactically valid in the wire format.
// Implementations may treat records with reserved field numbers as unknown.
func (n Number) IsValid() bool { func (n Number) IsValid() bool {
return MinValidNumber <= n && n < FirstReservedNumber || LastReservedNumber < n && n <= MaxValidNumber return MinValidNumber <= n && n <= MaxValidNumber
} }
// Type represents the wire type. // Type represents the wire type.
@@ -55,6 +52,7 @@ const (
errCodeOverflow errCodeOverflow
errCodeReserved errCodeReserved
errCodeEndGroup errCodeEndGroup
errCodeRecursionDepth
) )
var ( var (
@@ -89,7 +87,7 @@ func ParseError(n int) error {
// ConsumeField parses an entire field record (both tag and value) and returns // ConsumeField parses an entire field record (both tag and value) and returns
// the field number, the wire type, and the total length. // the field number, the wire type, and the total length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
// //
// The total length includes the tag header and the end group marker (if the // The total length includes the tag header and the end group marker (if the
// field is a group). // field is a group).
@@ -106,12 +104,16 @@ func ConsumeField(b []byte) (Number, Type, int) {
} }
// ConsumeFieldValue parses a field value and returns its length. // ConsumeFieldValue parses a field value and returns its length.
// This assumes that the field Number and wire Type have already been parsed. // This assumes that the field [Number] and wire [Type] have already been parsed.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
// //
// When parsing a group, the length includes the end group marker and // When parsing a group, the length includes the end group marker and
// the end group is verified to match the starting field number. // the end group is verified to match the starting field number.
func ConsumeFieldValue(num Number, typ Type, b []byte) (n int) { func ConsumeFieldValue(num Number, typ Type, b []byte) (n int) {
return consumeFieldValueD(num, typ, b, DefaultRecursionLimit)
}
func consumeFieldValueD(num Number, typ Type, b []byte, depth int) (n int) {
switch typ { switch typ {
case VarintType: case VarintType:
_, n = ConsumeVarint(b) _, n = ConsumeVarint(b)
@@ -126,6 +128,9 @@ func ConsumeFieldValue(num Number, typ Type, b []byte) (n int) {
_, n = ConsumeBytes(b) _, n = ConsumeBytes(b)
return n return n
case StartGroupType: case StartGroupType:
if depth < 0 {
return errCodeRecursionDepth
}
n0 := len(b) n0 := len(b)
for { for {
num2, typ2, n := ConsumeTag(b) num2, typ2, n := ConsumeTag(b)
@@ -140,7 +145,7 @@ func ConsumeFieldValue(num Number, typ Type, b []byte) (n int) {
return n0 - len(b) return n0 - len(b)
} }
n = ConsumeFieldValue(num2, typ2, b) n = consumeFieldValueD(num2, typ2, b, depth-1)
if n < 0 { if n < 0 {
return n // forward error code return n // forward error code
} }
@@ -159,7 +164,7 @@ func AppendTag(b []byte, num Number, typ Type) []byte {
} }
// ConsumeTag parses b as a varint-encoded tag, reporting its length. // ConsumeTag parses b as a varint-encoded tag, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeTag(b []byte) (Number, Type, int) { func ConsumeTag(b []byte) (Number, Type, int) {
v, n := ConsumeVarint(b) v, n := ConsumeVarint(b)
if n < 0 { if n < 0 {
@@ -258,7 +263,7 @@ func AppendVarint(b []byte, v uint64) []byte {
} }
// ConsumeVarint parses b as a varint-encoded uint64, reporting its length. // ConsumeVarint parses b as a varint-encoded uint64, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeVarint(b []byte) (v uint64, n int) { func ConsumeVarint(b []byte) (v uint64, n int) {
var y uint64 var y uint64
if len(b) <= 0 { if len(b) <= 0 {
@@ -379,7 +384,7 @@ func AppendFixed32(b []byte, v uint32) []byte {
} }
// ConsumeFixed32 parses b as a little-endian uint32, reporting its length. // ConsumeFixed32 parses b as a little-endian uint32, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeFixed32(b []byte) (v uint32, n int) { func ConsumeFixed32(b []byte) (v uint32, n int) {
if len(b) < 4 { if len(b) < 4 {
return 0, errCodeTruncated return 0, errCodeTruncated
@@ -407,7 +412,7 @@ func AppendFixed64(b []byte, v uint64) []byte {
} }
// ConsumeFixed64 parses b as a little-endian uint64, reporting its length. // ConsumeFixed64 parses b as a little-endian uint64, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeFixed64(b []byte) (v uint64, n int) { func ConsumeFixed64(b []byte) (v uint64, n int) {
if len(b) < 8 { if len(b) < 8 {
return 0, errCodeTruncated return 0, errCodeTruncated
@@ -427,7 +432,7 @@ func AppendBytes(b []byte, v []byte) []byte {
} }
// ConsumeBytes parses b as a length-prefixed bytes value, reporting its length. // ConsumeBytes parses b as a length-prefixed bytes value, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeBytes(b []byte) (v []byte, n int) { func ConsumeBytes(b []byte) (v []byte, n int) {
m, n := ConsumeVarint(b) m, n := ConsumeVarint(b)
if n < 0 { if n < 0 {
@@ -451,7 +456,7 @@ func AppendString(b []byte, v string) []byte {
} }
// ConsumeString parses b as a length-prefixed bytes value, reporting its length. // ConsumeString parses b as a length-prefixed bytes value, reporting its length.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeString(b []byte) (v string, n int) { func ConsumeString(b []byte) (v string, n int) {
bb, n := ConsumeBytes(b) bb, n := ConsumeBytes(b)
return string(bb), n return string(bb), n
@@ -466,7 +471,7 @@ func AppendGroup(b []byte, num Number, v []byte) []byte {
// ConsumeGroup parses b as a group value until the trailing end group marker, // ConsumeGroup parses b as a group value until the trailing end group marker,
// and verifies that the end marker matches the provided num. The value v // and verifies that the end marker matches the provided num. The value v
// does not contain the end marker, while the length does contain the end marker. // does not contain the end marker, while the length does contain the end marker.
// This returns a negative length upon an error (see ParseError). // This returns a negative length upon an error (see [ParseError]).
func ConsumeGroup(num Number, b []byte) (v []byte, n int) { func ConsumeGroup(num Number, b []byte) (v []byte, n int) {
n = ConsumeFieldValue(num, StartGroupType, b) n = ConsumeFieldValue(num, StartGroupType, b)
if n < 0 { if n < 0 {
@@ -490,8 +495,8 @@ func SizeGroup(num Number, n int) int {
return n + SizeTag(num) return n + SizeTag(num)
} }
// DecodeTag decodes the field Number and wire Type from its unified form. // DecodeTag decodes the field [Number] and wire [Type] from its unified form.
// The Number is -1 if the decoded field number overflows int32. // The [Number] is -1 if the decoded field number overflows int32.
// Other than overflow, this does not check for field number validity. // Other than overflow, this does not check for field number validity.
func DecodeTag(x uint64) (Number, Type) { func DecodeTag(x uint64) (Number, Type) {
// NOTE: MessageSet allows for larger field numbers than normal. // NOTE: MessageSet allows for larger field numbers than normal.
@@ -501,12 +506,13 @@ func DecodeTag(x uint64) (Number, Type) {
return Number(x >> 3), Type(x & 7) return Number(x >> 3), Type(x & 7)
} }
// EncodeTag encodes the field Number and wire Type into its unified form. // EncodeTag encodes the field [Number] and wire [Type] into its unified form.
func EncodeTag(num Number, typ Type) uint64 { func EncodeTag(num Number, typ Type) uint64 {
return uint64(num)<<3 | uint64(typ&7) return uint64(num)<<3 | uint64(typ&7)
} }
// DecodeZigZag decodes a zig-zag-encoded uint64 as an int64. // DecodeZigZag decodes a zig-zag-encoded uint64 as an int64.
//
// Input: {…, 5, 3, 1, 0, 2, 4, 6, …} // Input: {…, 5, 3, 1, 0, 2, 4, 6, …}
// Output: {…, -3, -2, -1, 0, +1, +2, +3, …} // Output: {…, -3, -2, -1, 0, +1, +2, +3, …}
func DecodeZigZag(x uint64) int64 { func DecodeZigZag(x uint64) int64 {
@@ -514,6 +520,7 @@ func DecodeZigZag(x uint64) int64 {
} }
// EncodeZigZag encodes an int64 as a zig-zag-encoded uint64. // EncodeZigZag encodes an int64 as a zig-zag-encoded uint64.
//
// Input: {…, -3, -2, -1, 0, +1, +2, +3, …} // Input: {…, -3, -2, -1, 0, +1, +2, +3, …}
// Output: {…, 5, 3, 1, 0, 2, 4, 6, …} // Output: {…, 5, 3, 1, 0, 2, 4, 6, …}
func EncodeZigZag(x int64) uint64 { func EncodeZigZag(x int64) uint64 {
@@ -521,6 +528,7 @@ func EncodeZigZag(x int64) uint64 {
} }
// DecodeBool decodes a uint64 as a bool. // DecodeBool decodes a uint64 as a bool.
//
// Input: { 0, 1, 2, …} // Input: { 0, 1, 2, …}
// Output: {false, true, true, …} // Output: {false, true, true, …}
func DecodeBool(x uint64) bool { func DecodeBool(x uint64) bool {
@@ -528,6 +536,7 @@ func DecodeBool(x uint64) bool {
} }
// EncodeBool encodes a bool as a uint64. // EncodeBool encodes a bool as a uint64.
//
// Input: {false, true} // Input: {false, true}
// Output: { 0, 1} // Output: { 0, 1}
func EncodeBool(x bool) uint64 { func EncodeBool(x bool) uint64 {

View File

@@ -14,7 +14,7 @@ import (
"google.golang.org/protobuf/internal/detrand" "google.golang.org/protobuf/internal/detrand"
"google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/pragma"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
type list interface { type list interface {
@@ -30,17 +30,17 @@ func formatListOpt(vs list, isRoot, allowMulti bool) string {
if isRoot { if isRoot {
var name string var name string
switch vs.(type) { switch vs.(type) {
case pref.Names: case protoreflect.Names:
name = "Names" name = "Names"
case pref.FieldNumbers: case protoreflect.FieldNumbers:
name = "FieldNumbers" name = "FieldNumbers"
case pref.FieldRanges: case protoreflect.FieldRanges:
name = "FieldRanges" name = "FieldRanges"
case pref.EnumRanges: case protoreflect.EnumRanges:
name = "EnumRanges" name = "EnumRanges"
case pref.FileImports: case protoreflect.FileImports:
name = "FileImports" name = "FileImports"
case pref.Descriptor: case protoreflect.Descriptor:
name = reflect.ValueOf(vs).MethodByName("Get").Type().Out(0).Name() + "s" name = reflect.ValueOf(vs).MethodByName("Get").Type().Out(0).Name() + "s"
default: default:
name = reflect.ValueOf(vs).Elem().Type().Name() name = reflect.ValueOf(vs).Elem().Type().Name()
@@ -50,17 +50,17 @@ func formatListOpt(vs list, isRoot, allowMulti bool) string {
var ss []string var ss []string
switch vs := vs.(type) { switch vs := vs.(type) {
case pref.Names: case protoreflect.Names:
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
ss = append(ss, fmt.Sprint(vs.Get(i))) ss = append(ss, fmt.Sprint(vs.Get(i)))
} }
return start + joinStrings(ss, false) + end return start + joinStrings(ss, false) + end
case pref.FieldNumbers: case protoreflect.FieldNumbers:
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
ss = append(ss, fmt.Sprint(vs.Get(i))) ss = append(ss, fmt.Sprint(vs.Get(i)))
} }
return start + joinStrings(ss, false) + end return start + joinStrings(ss, false) + end
case pref.FieldRanges: case protoreflect.FieldRanges:
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
r := vs.Get(i) r := vs.Get(i)
if r[0]+1 == r[1] { if r[0]+1 == r[1] {
@@ -70,7 +70,7 @@ func formatListOpt(vs list, isRoot, allowMulti bool) string {
} }
} }
return start + joinStrings(ss, false) + end return start + joinStrings(ss, false) + end
case pref.EnumRanges: case protoreflect.EnumRanges:
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
r := vs.Get(i) r := vs.Get(i)
if r[0] == r[1] { if r[0] == r[1] {
@@ -80,46 +80,44 @@ func formatListOpt(vs list, isRoot, allowMulti bool) string {
} }
} }
return start + joinStrings(ss, false) + end return start + joinStrings(ss, false) + end
case pref.FileImports: case protoreflect.FileImports:
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
var rs records var rs records
rs.Append(reflect.ValueOf(vs.Get(i)), "Path", "Package", "IsPublic", "IsWeak") rv := reflect.ValueOf(vs.Get(i))
rs.Append(rv, []methodAndName{
{rv.MethodByName("Path"), "Path"},
{rv.MethodByName("Package"), "Package"},
{rv.MethodByName("IsPublic"), "IsPublic"},
{rv.MethodByName("IsWeak"), "IsWeak"},
}...)
ss = append(ss, "{"+rs.Join()+"}") ss = append(ss, "{"+rs.Join()+"}")
} }
return start + joinStrings(ss, allowMulti) + end return start + joinStrings(ss, allowMulti) + end
default: default:
_, isEnumValue := vs.(pref.EnumValueDescriptors) _, isEnumValue := vs.(protoreflect.EnumValueDescriptors)
for i := 0; i < vs.Len(); i++ { for i := 0; i < vs.Len(); i++ {
m := reflect.ValueOf(vs).MethodByName("Get") m := reflect.ValueOf(vs).MethodByName("Get")
v := m.Call([]reflect.Value{reflect.ValueOf(i)})[0].Interface() v := m.Call([]reflect.Value{reflect.ValueOf(i)})[0].Interface()
ss = append(ss, formatDescOpt(v.(pref.Descriptor), false, allowMulti && !isEnumValue)) ss = append(ss, formatDescOpt(v.(protoreflect.Descriptor), false, allowMulti && !isEnumValue, nil))
} }
return start + joinStrings(ss, allowMulti && isEnumValue) + end return start + joinStrings(ss, allowMulti && isEnumValue) + end
} }
} }
// descriptorAccessors is a list of accessors to print for each descriptor. type methodAndName struct {
// method reflect.Value
// Do not print all accessors since some contain redundant information, name string
// while others are pointers that we do not want to follow since the descriptor
// is actually a cyclic graph.
//
// Using a list allows us to print the accessors in a sensible order.
var descriptorAccessors = map[reflect.Type][]string{
reflect.TypeOf((*pref.FileDescriptor)(nil)).Elem(): {"Path", "Package", "Imports", "Messages", "Enums", "Extensions", "Services"},
reflect.TypeOf((*pref.MessageDescriptor)(nil)).Elem(): {"IsMapEntry", "Fields", "Oneofs", "ReservedNames", "ReservedRanges", "RequiredNumbers", "ExtensionRanges", "Messages", "Enums", "Extensions"},
reflect.TypeOf((*pref.FieldDescriptor)(nil)).Elem(): {"Number", "Cardinality", "Kind", "HasJSONName", "JSONName", "HasPresence", "IsExtension", "IsPacked", "IsWeak", "IsList", "IsMap", "MapKey", "MapValue", "HasDefault", "Default", "ContainingOneof", "ContainingMessage", "Message", "Enum"},
reflect.TypeOf((*pref.OneofDescriptor)(nil)).Elem(): {"Fields"}, // not directly used; must keep in sync with formatDescOpt
reflect.TypeOf((*pref.EnumDescriptor)(nil)).Elem(): {"Values", "ReservedNames", "ReservedRanges"},
reflect.TypeOf((*pref.EnumValueDescriptor)(nil)).Elem(): {"Number"},
reflect.TypeOf((*pref.ServiceDescriptor)(nil)).Elem(): {"Methods"},
reflect.TypeOf((*pref.MethodDescriptor)(nil)).Elem(): {"Input", "Output", "IsStreamingClient", "IsStreamingServer"},
} }
func FormatDesc(s fmt.State, r rune, t pref.Descriptor) { func FormatDesc(s fmt.State, r rune, t protoreflect.Descriptor) {
io.WriteString(s, formatDescOpt(t, true, r == 'v' && (s.Flag('+') || s.Flag('#')))) io.WriteString(s, formatDescOpt(t, true, r == 'v' && (s.Flag('+') || s.Flag('#')), nil))
} }
func formatDescOpt(t pref.Descriptor, isRoot, allowMulti bool) string {
func InternalFormatDescOptForTesting(t protoreflect.Descriptor, isRoot, allowMulti bool, record func(string)) string {
return formatDescOpt(t, isRoot, allowMulti, record)
}
func formatDescOpt(t protoreflect.Descriptor, isRoot, allowMulti bool, record func(string)) string {
rv := reflect.ValueOf(t) rv := reflect.ValueOf(t)
rt := rv.MethodByName("ProtoType").Type().In(0) rt := rv.MethodByName("ProtoType").Type().In(0)
@@ -128,27 +126,61 @@ func formatDescOpt(t pref.Descriptor, isRoot, allowMulti bool) string {
start = rt.Name() + "{" start = rt.Name() + "{"
} }
_, isFile := t.(pref.FileDescriptor) _, isFile := t.(protoreflect.FileDescriptor)
rs := records{allowMulti: allowMulti} rs := records{
allowMulti: allowMulti,
record: record,
}
if t.IsPlaceholder() { if t.IsPlaceholder() {
if isFile { if isFile {
rs.Append(rv, "Path", "Package", "IsPlaceholder") rs.Append(rv, []methodAndName{
{rv.MethodByName("Path"), "Path"},
{rv.MethodByName("Package"), "Package"},
{rv.MethodByName("IsPlaceholder"), "IsPlaceholder"},
}...)
} else { } else {
rs.Append(rv, "FullName", "IsPlaceholder") rs.Append(rv, []methodAndName{
{rv.MethodByName("FullName"), "FullName"},
{rv.MethodByName("IsPlaceholder"), "IsPlaceholder"},
}...)
} }
} else { } else {
switch { switch {
case isFile: case isFile:
rs.Append(rv, "Syntax") rs.Append(rv, methodAndName{rv.MethodByName("Syntax"), "Syntax"})
case isRoot: case isRoot:
rs.Append(rv, "Syntax", "FullName") rs.Append(rv, []methodAndName{
{rv.MethodByName("Syntax"), "Syntax"},
{rv.MethodByName("FullName"), "FullName"},
}...)
default: default:
rs.Append(rv, "Name") rs.Append(rv, methodAndName{rv.MethodByName("Name"), "Name"})
} }
switch t := t.(type) { switch t := t.(type) {
case pref.FieldDescriptor: case protoreflect.FieldDescriptor:
for _, s := range descriptorAccessors[rt] { accessors := []methodAndName{
switch s { {rv.MethodByName("Number"), "Number"},
{rv.MethodByName("Cardinality"), "Cardinality"},
{rv.MethodByName("Kind"), "Kind"},
{rv.MethodByName("HasJSONName"), "HasJSONName"},
{rv.MethodByName("JSONName"), "JSONName"},
{rv.MethodByName("HasPresence"), "HasPresence"},
{rv.MethodByName("IsExtension"), "IsExtension"},
{rv.MethodByName("IsPacked"), "IsPacked"},
{rv.MethodByName("IsWeak"), "IsWeak"},
{rv.MethodByName("IsList"), "IsList"},
{rv.MethodByName("IsMap"), "IsMap"},
{rv.MethodByName("MapKey"), "MapKey"},
{rv.MethodByName("MapValue"), "MapValue"},
{rv.MethodByName("HasDefault"), "HasDefault"},
{rv.MethodByName("Default"), "Default"},
{rv.MethodByName("ContainingOneof"), "ContainingOneof"},
{rv.MethodByName("ContainingMessage"), "ContainingMessage"},
{rv.MethodByName("Message"), "Message"},
{rv.MethodByName("Enum"), "Enum"},
}
for _, s := range accessors {
switch s.name {
case "MapKey": case "MapKey":
if k := t.MapKey(); k != nil { if k := t.MapKey(); k != nil {
rs.recs = append(rs.recs, [2]string{"MapKey", k.Kind().String()}) rs.recs = append(rs.recs, [2]string{"MapKey", k.Kind().String()})
@@ -156,21 +188,21 @@ func formatDescOpt(t pref.Descriptor, isRoot, allowMulti bool) string {
case "MapValue": case "MapValue":
if v := t.MapValue(); v != nil { if v := t.MapValue(); v != nil {
switch v.Kind() { switch v.Kind() {
case pref.EnumKind: case protoreflect.EnumKind:
rs.recs = append(rs.recs, [2]string{"MapValue", string(v.Enum().FullName())}) rs.AppendRecs("MapValue", [2]string{"MapValue", string(v.Enum().FullName())})
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
rs.recs = append(rs.recs, [2]string{"MapValue", string(v.Message().FullName())}) rs.AppendRecs("MapValue", [2]string{"MapValue", string(v.Message().FullName())})
default: default:
rs.recs = append(rs.recs, [2]string{"MapValue", v.Kind().String()}) rs.AppendRecs("MapValue", [2]string{"MapValue", v.Kind().String()})
} }
} }
case "ContainingOneof": case "ContainingOneof":
if od := t.ContainingOneof(); od != nil { if od := t.ContainingOneof(); od != nil {
rs.recs = append(rs.recs, [2]string{"Oneof", string(od.Name())}) rs.AppendRecs("ContainingOneof", [2]string{"Oneof", string(od.Name())})
} }
case "ContainingMessage": case "ContainingMessage":
if t.IsExtension() { if t.IsExtension() {
rs.recs = append(rs.recs, [2]string{"Extendee", string(t.ContainingMessage().FullName())}) rs.AppendRecs("ContainingMessage", [2]string{"Extendee", string(t.ContainingMessage().FullName())})
} }
case "Message": case "Message":
if !t.IsMap() { if !t.IsMap() {
@@ -180,20 +212,68 @@ func formatDescOpt(t pref.Descriptor, isRoot, allowMulti bool) string {
rs.Append(rv, s) rs.Append(rv, s)
} }
} }
case pref.OneofDescriptor: case protoreflect.OneofDescriptor:
var ss []string var ss []string
fs := t.Fields() fs := t.Fields()
for i := 0; i < fs.Len(); i++ { for i := 0; i < fs.Len(); i++ {
ss = append(ss, string(fs.Get(i).Name())) ss = append(ss, string(fs.Get(i).Name()))
} }
if len(ss) > 0 { if len(ss) > 0 {
rs.recs = append(rs.recs, [2]string{"Fields", "[" + joinStrings(ss, false) + "]"}) rs.AppendRecs("Fields", [2]string{"Fields", "[" + joinStrings(ss, false) + "]"})
} }
default:
rs.Append(rv, descriptorAccessors[rt]...) case protoreflect.FileDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("Path"), "Path"},
{rv.MethodByName("Package"), "Package"},
{rv.MethodByName("Imports"), "Imports"},
{rv.MethodByName("Messages"), "Messages"},
{rv.MethodByName("Enums"), "Enums"},
{rv.MethodByName("Extensions"), "Extensions"},
{rv.MethodByName("Services"), "Services"},
}...)
case protoreflect.MessageDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("IsMapEntry"), "IsMapEntry"},
{rv.MethodByName("Fields"), "Fields"},
{rv.MethodByName("Oneofs"), "Oneofs"},
{rv.MethodByName("ReservedNames"), "ReservedNames"},
{rv.MethodByName("ReservedRanges"), "ReservedRanges"},
{rv.MethodByName("RequiredNumbers"), "RequiredNumbers"},
{rv.MethodByName("ExtensionRanges"), "ExtensionRanges"},
{rv.MethodByName("Messages"), "Messages"},
{rv.MethodByName("Enums"), "Enums"},
{rv.MethodByName("Extensions"), "Extensions"},
}...)
case protoreflect.EnumDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("Values"), "Values"},
{rv.MethodByName("ReservedNames"), "ReservedNames"},
{rv.MethodByName("ReservedRanges"), "ReservedRanges"},
}...)
case protoreflect.EnumValueDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("Number"), "Number"},
}...)
case protoreflect.ServiceDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("Methods"), "Methods"},
}...)
case protoreflect.MethodDescriptor:
rs.Append(rv, []methodAndName{
{rv.MethodByName("Input"), "Input"},
{rv.MethodByName("Output"), "Output"},
{rv.MethodByName("IsStreamingClient"), "IsStreamingClient"},
{rv.MethodByName("IsStreamingServer"), "IsStreamingServer"},
}...)
} }
if rv.MethodByName("GoType").IsValid() { if m := rv.MethodByName("GoType"); m.IsValid() {
rs.Append(rv, "GoType") rs.Append(rv, methodAndName{m, "GoType"})
} }
} }
return start + rs.Join() + end return start + rs.Join() + end
@@ -202,21 +282,36 @@ func formatDescOpt(t pref.Descriptor, isRoot, allowMulti bool) string {
type records struct { type records struct {
recs [][2]string recs [][2]string
allowMulti bool allowMulti bool
// record is a function that will be called for every Append() or
// AppendRecs() call, to be used for testing with the
// InternalFormatDescOptForTesting function.
record func(string)
} }
func (rs *records) Append(v reflect.Value, accessors ...string) { func (rs *records) AppendRecs(fieldName string, newRecs [2]string) {
if rs.record != nil {
rs.record(fieldName)
}
rs.recs = append(rs.recs, newRecs)
}
func (rs *records) Append(v reflect.Value, accessors ...methodAndName) {
for _, a := range accessors { for _, a := range accessors {
if rs.record != nil {
rs.record(a.name)
}
var rv reflect.Value var rv reflect.Value
if m := v.MethodByName(a); m.IsValid() { if a.method.IsValid() {
rv = m.Call(nil)[0] rv = a.method.Call(nil)[0]
} }
if v.Kind() == reflect.Struct && !rv.IsValid() { if v.Kind() == reflect.Struct && !rv.IsValid() {
rv = v.FieldByName(a) rv = v.FieldByName(a.name)
} }
if !rv.IsValid() { if !rv.IsValid() {
panic(fmt.Sprintf("unknown accessor: %v.%s", v.Type(), a)) panic(fmt.Sprintf("unknown accessor: %v.%s", v.Type(), a.name))
} }
if _, ok := rv.Interface().(pref.Value); ok { if _, ok := rv.Interface().(protoreflect.Value); ok {
rv = rv.MethodByName("Interface").Call(nil)[0] rv = rv.MethodByName("Interface").Call(nil)[0]
if !rv.IsNil() { if !rv.IsNil() {
rv = rv.Elem() rv = rv.Elem()
@@ -250,9 +345,9 @@ func (rs *records) Append(v reflect.Value, accessors ...string) {
switch v := v.(type) { switch v := v.(type) {
case list: case list:
s = formatListOpt(v, false, rs.allowMulti) s = formatListOpt(v, false, rs.allowMulti)
case pref.FieldDescriptor, pref.OneofDescriptor, pref.EnumValueDescriptor, pref.MethodDescriptor: case protoreflect.FieldDescriptor, protoreflect.OneofDescriptor, protoreflect.EnumValueDescriptor, protoreflect.MethodDescriptor:
s = string(v.(pref.Descriptor).Name()) s = string(v.(protoreflect.Descriptor).Name())
case pref.Descriptor: case protoreflect.Descriptor:
s = string(v.FullName()) s = string(v.FullName())
case string: case string:
s = strconv.Quote(v) s = strconv.Quote(v)
@@ -261,7 +356,7 @@ func (rs *records) Append(v reflect.Value, accessors ...string) {
default: default:
s = fmt.Sprint(v) s = fmt.Sprint(v)
} }
rs.recs = append(rs.recs, [2]string{a, s}) rs.recs = append(rs.recs, [2]string{a.name, s})
} }
} }

View File

@@ -0,0 +1,12 @@
// Copyright 2024 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Package editiondefaults contains the binary representation of the editions
// defaults.
package editiondefaults
import _ "embed"
//go:embed editions_defaults.binpb
var Defaults []byte

View File

@@ -0,0 +1,4 @@
  (0ж
  (0з
  (0и ж

View File

@@ -15,8 +15,8 @@ import (
"strconv" "strconv"
ptext "google.golang.org/protobuf/internal/encoding/text" ptext "google.golang.org/protobuf/internal/encoding/text"
errors "google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
// Format is the serialization format used to represent the default value. // Format is the serialization format used to represent the default value.
@@ -35,56 +35,56 @@ const (
// Unmarshal deserializes the default string s according to the given kind k. // Unmarshal deserializes the default string s according to the given kind k.
// When k is an enum, a list of enum value descriptors must be provided. // When k is an enum, a list of enum value descriptors must be provided.
func Unmarshal(s string, k pref.Kind, evs pref.EnumValueDescriptors, f Format) (pref.Value, pref.EnumValueDescriptor, error) { func Unmarshal(s string, k protoreflect.Kind, evs protoreflect.EnumValueDescriptors, f Format) (protoreflect.Value, protoreflect.EnumValueDescriptor, error) {
switch k { switch k {
case pref.BoolKind: case protoreflect.BoolKind:
if f == GoTag { if f == GoTag {
switch s { switch s {
case "1": case "1":
return pref.ValueOfBool(true), nil, nil return protoreflect.ValueOfBool(true), nil, nil
case "0": case "0":
return pref.ValueOfBool(false), nil, nil return protoreflect.ValueOfBool(false), nil, nil
} }
} else { } else {
switch s { switch s {
case "true": case "true":
return pref.ValueOfBool(true), nil, nil return protoreflect.ValueOfBool(true), nil, nil
case "false": case "false":
return pref.ValueOfBool(false), nil, nil return protoreflect.ValueOfBool(false), nil, nil
} }
} }
case pref.EnumKind: case protoreflect.EnumKind:
if f == GoTag { if f == GoTag {
// Go tags use the numeric form of the enum value. // Go tags use the numeric form of the enum value.
if n, err := strconv.ParseInt(s, 10, 32); err == nil { if n, err := strconv.ParseInt(s, 10, 32); err == nil {
if ev := evs.ByNumber(pref.EnumNumber(n)); ev != nil { if ev := evs.ByNumber(protoreflect.EnumNumber(n)); ev != nil {
return pref.ValueOfEnum(ev.Number()), ev, nil return protoreflect.ValueOfEnum(ev.Number()), ev, nil
} }
} }
} else { } else {
// Descriptor default_value use the enum identifier. // Descriptor default_value use the enum identifier.
ev := evs.ByName(pref.Name(s)) ev := evs.ByName(protoreflect.Name(s))
if ev != nil { if ev != nil {
return pref.ValueOfEnum(ev.Number()), ev, nil return protoreflect.ValueOfEnum(ev.Number()), ev, nil
} }
} }
case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind: case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind:
if v, err := strconv.ParseInt(s, 10, 32); err == nil { if v, err := strconv.ParseInt(s, 10, 32); err == nil {
return pref.ValueOfInt32(int32(v)), nil, nil return protoreflect.ValueOfInt32(int32(v)), nil, nil
} }
case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind: case protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
if v, err := strconv.ParseInt(s, 10, 64); err == nil { if v, err := strconv.ParseInt(s, 10, 64); err == nil {
return pref.ValueOfInt64(int64(v)), nil, nil return protoreflect.ValueOfInt64(int64(v)), nil, nil
} }
case pref.Uint32Kind, pref.Fixed32Kind: case protoreflect.Uint32Kind, protoreflect.Fixed32Kind:
if v, err := strconv.ParseUint(s, 10, 32); err == nil { if v, err := strconv.ParseUint(s, 10, 32); err == nil {
return pref.ValueOfUint32(uint32(v)), nil, nil return protoreflect.ValueOfUint32(uint32(v)), nil, nil
} }
case pref.Uint64Kind, pref.Fixed64Kind: case protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
if v, err := strconv.ParseUint(s, 10, 64); err == nil { if v, err := strconv.ParseUint(s, 10, 64); err == nil {
return pref.ValueOfUint64(uint64(v)), nil, nil return protoreflect.ValueOfUint64(uint64(v)), nil, nil
} }
case pref.FloatKind, pref.DoubleKind: case protoreflect.FloatKind, protoreflect.DoubleKind:
var v float64 var v float64
var err error var err error
switch s { switch s {
@@ -98,29 +98,29 @@ func Unmarshal(s string, k pref.Kind, evs pref.EnumValueDescriptors, f Format) (
v, err = strconv.ParseFloat(s, 64) v, err = strconv.ParseFloat(s, 64)
} }
if err == nil { if err == nil {
if k == pref.FloatKind { if k == protoreflect.FloatKind {
return pref.ValueOfFloat32(float32(v)), nil, nil return protoreflect.ValueOfFloat32(float32(v)), nil, nil
} else { } else {
return pref.ValueOfFloat64(float64(v)), nil, nil return protoreflect.ValueOfFloat64(float64(v)), nil, nil
} }
} }
case pref.StringKind: case protoreflect.StringKind:
// String values are already unescaped and can be used as is. // String values are already unescaped and can be used as is.
return pref.ValueOfString(s), nil, nil return protoreflect.ValueOfString(s), nil, nil
case pref.BytesKind: case protoreflect.BytesKind:
if b, ok := unmarshalBytes(s); ok { if b, ok := unmarshalBytes(s); ok {
return pref.ValueOfBytes(b), nil, nil return protoreflect.ValueOfBytes(b), nil, nil
} }
} }
return pref.Value{}, nil, errors.New("could not parse value for %v: %q", k, s) return protoreflect.Value{}, nil, errors.New("could not parse value for %v: %q", k, s)
} }
// Marshal serializes v as the default string according to the given kind k. // Marshal serializes v as the default string according to the given kind k.
// When specifying the Descriptor format for an enum kind, the associated // When specifying the Descriptor format for an enum kind, the associated
// enum value descriptor must be provided. // enum value descriptor must be provided.
func Marshal(v pref.Value, ev pref.EnumValueDescriptor, k pref.Kind, f Format) (string, error) { func Marshal(v protoreflect.Value, ev protoreflect.EnumValueDescriptor, k protoreflect.Kind, f Format) (string, error) {
switch k { switch k {
case pref.BoolKind: case protoreflect.BoolKind:
if f == GoTag { if f == GoTag {
if v.Bool() { if v.Bool() {
return "1", nil return "1", nil
@@ -134,17 +134,17 @@ func Marshal(v pref.Value, ev pref.EnumValueDescriptor, k pref.Kind, f Format) (
return "false", nil return "false", nil
} }
} }
case pref.EnumKind: case protoreflect.EnumKind:
if f == GoTag { if f == GoTag {
return strconv.FormatInt(int64(v.Enum()), 10), nil return strconv.FormatInt(int64(v.Enum()), 10), nil
} else { } else {
return string(ev.Name()), nil return string(ev.Name()), nil
} }
case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind, pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind: case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind, protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
return strconv.FormatInt(v.Int(), 10), nil return strconv.FormatInt(v.Int(), 10), nil
case pref.Uint32Kind, pref.Fixed32Kind, pref.Uint64Kind, pref.Fixed64Kind: case protoreflect.Uint32Kind, protoreflect.Fixed32Kind, protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
return strconv.FormatUint(v.Uint(), 10), nil return strconv.FormatUint(v.Uint(), 10), nil
case pref.FloatKind, pref.DoubleKind: case protoreflect.FloatKind, protoreflect.DoubleKind:
f := v.Float() f := v.Float()
switch { switch {
case math.IsInf(f, -1): case math.IsInf(f, -1):
@@ -154,16 +154,16 @@ func Marshal(v pref.Value, ev pref.EnumValueDescriptor, k pref.Kind, f Format) (
case math.IsNaN(f): case math.IsNaN(f):
return "nan", nil return "nan", nil
default: default:
if k == pref.FloatKind { if k == protoreflect.FloatKind {
return strconv.FormatFloat(f, 'g', -1, 32), nil return strconv.FormatFloat(f, 'g', -1, 32), nil
} else { } else {
return strconv.FormatFloat(f, 'g', -1, 64), nil return strconv.FormatFloat(f, 'g', -1, 64), nil
} }
} }
case pref.StringKind: case protoreflect.StringKind:
// String values are serialized as is without any escaping. // String values are serialized as is without any escaping.
return v.String(), nil return v.String(), nil
case pref.BytesKind: case protoreflect.BytesKind:
if s, ok := marshalBytes(v.Bytes()); ok { if s, ok := marshalBytes(v.Bytes()); ok {
return s, nil return s, nil
} }

View File

@@ -10,7 +10,7 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
// The MessageSet wire format is equivalent to a message defined as follows, // The MessageSet wire format is equivalent to a message defined as follows,
@@ -33,6 +33,7 @@ const (
// ExtensionName is the field name for extensions of MessageSet. // ExtensionName is the field name for extensions of MessageSet.
// //
// A valid MessageSet extension must be of the form: // A valid MessageSet extension must be of the form:
//
// message MyMessage { // message MyMessage {
// extend proto2.bridge.MessageSet { // extend proto2.bridge.MessageSet {
// optional MyMessage message_set_extension = 1234; // optional MyMessage message_set_extension = 1234;
@@ -42,13 +43,13 @@ const (
const ExtensionName = "message_set_extension" const ExtensionName = "message_set_extension"
// IsMessageSet returns whether the message uses the MessageSet wire format. // IsMessageSet returns whether the message uses the MessageSet wire format.
func IsMessageSet(md pref.MessageDescriptor) bool { func IsMessageSet(md protoreflect.MessageDescriptor) bool {
xmd, ok := md.(interface{ IsMessageSet() bool }) xmd, ok := md.(interface{ IsMessageSet() bool })
return ok && xmd.IsMessageSet() return ok && xmd.IsMessageSet()
} }
// IsMessageSetExtension reports this field properly extends a MessageSet. // IsMessageSetExtension reports this field properly extends a MessageSet.
func IsMessageSetExtension(fd pref.FieldDescriptor) bool { func IsMessageSetExtension(fd protoreflect.FieldDescriptor) bool {
switch { switch {
case fd.Name() != ExtensionName: case fd.Name() != ExtensionName:
return false return false

View File

@@ -11,10 +11,10 @@ import (
"strconv" "strconv"
"strings" "strings"
defval "google.golang.org/protobuf/internal/encoding/defval" "google.golang.org/protobuf/internal/encoding/defval"
fdesc "google.golang.org/protobuf/internal/filedesc" "google.golang.org/protobuf/internal/filedesc"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
var byteType = reflect.TypeOf(byte(0)) var byteType = reflect.TypeOf(byte(0))
@@ -29,9 +29,9 @@ var byteType = reflect.TypeOf(byte(0))
// This does not populate the Enum or Message (except for weak message). // This does not populate the Enum or Message (except for weak message).
// //
// This function is a best effort attempt; parsing errors are ignored. // This function is a best effort attempt; parsing errors are ignored.
func Unmarshal(tag string, goType reflect.Type, evs pref.EnumValueDescriptors) pref.FieldDescriptor { func Unmarshal(tag string, goType reflect.Type, evs protoreflect.EnumValueDescriptors) protoreflect.FieldDescriptor {
f := new(fdesc.Field) f := new(filedesc.Field)
f.L0.ParentFile = fdesc.SurrogateProto2 f.L0.ParentFile = filedesc.SurrogateProto2
for len(tag) > 0 { for len(tag) > 0 {
i := strings.IndexByte(tag, ',') i := strings.IndexByte(tag, ',')
if i < 0 { if i < 0 {
@@ -39,68 +39,68 @@ func Unmarshal(tag string, goType reflect.Type, evs pref.EnumValueDescriptors) p
} }
switch s := tag[:i]; { switch s := tag[:i]; {
case strings.HasPrefix(s, "name="): case strings.HasPrefix(s, "name="):
f.L0.FullName = pref.FullName(s[len("name="):]) f.L0.FullName = protoreflect.FullName(s[len("name="):])
case strings.Trim(s, "0123456789") == "": case strings.Trim(s, "0123456789") == "":
n, _ := strconv.ParseUint(s, 10, 32) n, _ := strconv.ParseUint(s, 10, 32)
f.L1.Number = pref.FieldNumber(n) f.L1.Number = protoreflect.FieldNumber(n)
case s == "opt": case s == "opt":
f.L1.Cardinality = pref.Optional f.L1.Cardinality = protoreflect.Optional
case s == "req": case s == "req":
f.L1.Cardinality = pref.Required f.L1.Cardinality = protoreflect.Required
case s == "rep": case s == "rep":
f.L1.Cardinality = pref.Repeated f.L1.Cardinality = protoreflect.Repeated
case s == "varint": case s == "varint":
switch goType.Kind() { switch goType.Kind() {
case reflect.Bool: case reflect.Bool:
f.L1.Kind = pref.BoolKind f.L1.Kind = protoreflect.BoolKind
case reflect.Int32: case reflect.Int32:
f.L1.Kind = pref.Int32Kind f.L1.Kind = protoreflect.Int32Kind
case reflect.Int64: case reflect.Int64:
f.L1.Kind = pref.Int64Kind f.L1.Kind = protoreflect.Int64Kind
case reflect.Uint32: case reflect.Uint32:
f.L1.Kind = pref.Uint32Kind f.L1.Kind = protoreflect.Uint32Kind
case reflect.Uint64: case reflect.Uint64:
f.L1.Kind = pref.Uint64Kind f.L1.Kind = protoreflect.Uint64Kind
} }
case s == "zigzag32": case s == "zigzag32":
if goType.Kind() == reflect.Int32 { if goType.Kind() == reflect.Int32 {
f.L1.Kind = pref.Sint32Kind f.L1.Kind = protoreflect.Sint32Kind
} }
case s == "zigzag64": case s == "zigzag64":
if goType.Kind() == reflect.Int64 { if goType.Kind() == reflect.Int64 {
f.L1.Kind = pref.Sint64Kind f.L1.Kind = protoreflect.Sint64Kind
} }
case s == "fixed32": case s == "fixed32":
switch goType.Kind() { switch goType.Kind() {
case reflect.Int32: case reflect.Int32:
f.L1.Kind = pref.Sfixed32Kind f.L1.Kind = protoreflect.Sfixed32Kind
case reflect.Uint32: case reflect.Uint32:
f.L1.Kind = pref.Fixed32Kind f.L1.Kind = protoreflect.Fixed32Kind
case reflect.Float32: case reflect.Float32:
f.L1.Kind = pref.FloatKind f.L1.Kind = protoreflect.FloatKind
} }
case s == "fixed64": case s == "fixed64":
switch goType.Kind() { switch goType.Kind() {
case reflect.Int64: case reflect.Int64:
f.L1.Kind = pref.Sfixed64Kind f.L1.Kind = protoreflect.Sfixed64Kind
case reflect.Uint64: case reflect.Uint64:
f.L1.Kind = pref.Fixed64Kind f.L1.Kind = protoreflect.Fixed64Kind
case reflect.Float64: case reflect.Float64:
f.L1.Kind = pref.DoubleKind f.L1.Kind = protoreflect.DoubleKind
} }
case s == "bytes": case s == "bytes":
switch { switch {
case goType.Kind() == reflect.String: case goType.Kind() == reflect.String:
f.L1.Kind = pref.StringKind f.L1.Kind = protoreflect.StringKind
case goType.Kind() == reflect.Slice && goType.Elem() == byteType: case goType.Kind() == reflect.Slice && goType.Elem() == byteType:
f.L1.Kind = pref.BytesKind f.L1.Kind = protoreflect.BytesKind
default: default:
f.L1.Kind = pref.MessageKind f.L1.Kind = protoreflect.MessageKind
} }
case s == "group": case s == "group":
f.L1.Kind = pref.GroupKind f.L1.Kind = protoreflect.GroupKind
case strings.HasPrefix(s, "enum="): case strings.HasPrefix(s, "enum="):
f.L1.Kind = pref.EnumKind f.L1.Kind = protoreflect.EnumKind
case strings.HasPrefix(s, "json="): case strings.HasPrefix(s, "json="):
jsonName := s[len("json="):] jsonName := s[len("json="):]
if jsonName != strs.JSONCamelCase(string(f.L0.FullName.Name())) { if jsonName != strs.JSONCamelCase(string(f.L0.FullName.Name())) {
@@ -111,23 +111,23 @@ func Unmarshal(tag string, goType reflect.Type, evs pref.EnumValueDescriptors) p
f.L1.IsPacked = true f.L1.IsPacked = true
case strings.HasPrefix(s, "weak="): case strings.HasPrefix(s, "weak="):
f.L1.IsWeak = true f.L1.IsWeak = true
f.L1.Message = fdesc.PlaceholderMessage(pref.FullName(s[len("weak="):])) f.L1.Message = filedesc.PlaceholderMessage(protoreflect.FullName(s[len("weak="):]))
case strings.HasPrefix(s, "def="): case strings.HasPrefix(s, "def="):
// The default tag is special in that everything afterwards is the // The default tag is special in that everything afterwards is the
// default regardless of the presence of commas. // default regardless of the presence of commas.
s, i = tag[len("def="):], len(tag) s, i = tag[len("def="):], len(tag)
v, ev, _ := defval.Unmarshal(s, f.L1.Kind, evs, defval.GoTag) v, ev, _ := defval.Unmarshal(s, f.L1.Kind, evs, defval.GoTag)
f.L1.Default = fdesc.DefaultValue(v, ev) f.L1.Default = filedesc.DefaultValue(v, ev)
case s == "proto3": case s == "proto3":
f.L0.ParentFile = fdesc.SurrogateProto3 f.L0.ParentFile = filedesc.SurrogateProto3
} }
tag = strings.TrimPrefix(tag[i:], ",") tag = strings.TrimPrefix(tag[i:], ",")
} }
// The generator uses the group message name instead of the field name. // The generator uses the group message name instead of the field name.
// We obtain the real field name by lowercasing the group name. // We obtain the real field name by lowercasing the group name.
if f.L1.Kind == pref.GroupKind { if f.L1.Kind == protoreflect.GroupKind {
f.L0.FullName = pref.FullName(strings.ToLower(string(f.L0.FullName))) f.L0.FullName = protoreflect.FullName(strings.ToLower(string(f.L0.FullName)))
} }
return f return f
} }
@@ -140,38 +140,38 @@ func Unmarshal(tag string, goType reflect.Type, evs pref.EnumValueDescriptors) p
// Depending on the context on how Marshal is called, there are different ways // Depending on the context on how Marshal is called, there are different ways
// through which that information is determined. As such it is the caller's // through which that information is determined. As such it is the caller's
// responsibility to provide a function to obtain that information. // responsibility to provide a function to obtain that information.
func Marshal(fd pref.FieldDescriptor, enumName string) string { func Marshal(fd protoreflect.FieldDescriptor, enumName string) string {
var tag []string var tag []string
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind, pref.EnumKind, pref.Int32Kind, pref.Uint32Kind, pref.Int64Kind, pref.Uint64Kind: case protoreflect.BoolKind, protoreflect.EnumKind, protoreflect.Int32Kind, protoreflect.Uint32Kind, protoreflect.Int64Kind, protoreflect.Uint64Kind:
tag = append(tag, "varint") tag = append(tag, "varint")
case pref.Sint32Kind: case protoreflect.Sint32Kind:
tag = append(tag, "zigzag32") tag = append(tag, "zigzag32")
case pref.Sint64Kind: case protoreflect.Sint64Kind:
tag = append(tag, "zigzag64") tag = append(tag, "zigzag64")
case pref.Sfixed32Kind, pref.Fixed32Kind, pref.FloatKind: case protoreflect.Sfixed32Kind, protoreflect.Fixed32Kind, protoreflect.FloatKind:
tag = append(tag, "fixed32") tag = append(tag, "fixed32")
case pref.Sfixed64Kind, pref.Fixed64Kind, pref.DoubleKind: case protoreflect.Sfixed64Kind, protoreflect.Fixed64Kind, protoreflect.DoubleKind:
tag = append(tag, "fixed64") tag = append(tag, "fixed64")
case pref.StringKind, pref.BytesKind, pref.MessageKind: case protoreflect.StringKind, protoreflect.BytesKind, protoreflect.MessageKind:
tag = append(tag, "bytes") tag = append(tag, "bytes")
case pref.GroupKind: case protoreflect.GroupKind:
tag = append(tag, "group") tag = append(tag, "group")
} }
tag = append(tag, strconv.Itoa(int(fd.Number()))) tag = append(tag, strconv.Itoa(int(fd.Number())))
switch fd.Cardinality() { switch fd.Cardinality() {
case pref.Optional: case protoreflect.Optional:
tag = append(tag, "opt") tag = append(tag, "opt")
case pref.Required: case protoreflect.Required:
tag = append(tag, "req") tag = append(tag, "req")
case pref.Repeated: case protoreflect.Repeated:
tag = append(tag, "rep") tag = append(tag, "rep")
} }
if fd.IsPacked() { if fd.IsPacked() {
tag = append(tag, "packed") tag = append(tag, "packed")
} }
name := string(fd.Name()) name := string(fd.Name())
if fd.Kind() == pref.GroupKind { if fd.Kind() == protoreflect.GroupKind {
// The name of the FieldDescriptor for a group field is // The name of the FieldDescriptor for a group field is
// lowercased. To find the original capitalization, we // lowercased. To find the original capitalization, we
// look in the field's MessageType. // look in the field's MessageType.
@@ -189,10 +189,10 @@ func Marshal(fd pref.FieldDescriptor, enumName string) string {
// The previous implementation does not tag extension fields as proto3, // The previous implementation does not tag extension fields as proto3,
// even when the field is defined in a proto3 file. Match that behavior // even when the field is defined in a proto3 file. Match that behavior
// for consistency. // for consistency.
if fd.Syntax() == pref.Proto3 && !fd.IsExtension() { if fd.Syntax() == protoreflect.Proto3 && !fd.IsExtension() {
tag = append(tag, "proto3") tag = append(tag, "proto3")
} }
if fd.Kind() == pref.EnumKind && enumName != "" { if fd.Kind() == protoreflect.EnumKind && enumName != "" {
tag = append(tag, "enum="+enumName) tag = append(tag, "enum="+enumName)
} }
if fd.ContainingOneof() != nil { if fd.ContainingOneof() != nil {

View File

@@ -8,7 +8,6 @@ import (
"bytes" "bytes"
"fmt" "fmt"
"io" "io"
"regexp"
"strconv" "strconv"
"unicode/utf8" "unicode/utf8"
@@ -381,7 +380,7 @@ func (d *Decoder) currentOpenKind() (Kind, byte) {
case '[': case '[':
return ListOpen, ']' return ListOpen, ']'
} }
panic(fmt.Sprintf("Decoder: openStack contains invalid byte %s", string(openCh))) panic(fmt.Sprintf("Decoder: openStack contains invalid byte %c", openCh))
} }
func (d *Decoder) pushOpenStack(ch byte) { func (d *Decoder) pushOpenStack(ch byte) {
@@ -413,15 +412,16 @@ func (d *Decoder) parseFieldName() (tok Token, err error) {
// Field number. Identify if input is a valid number that is not negative // Field number. Identify if input is a valid number that is not negative
// and is decimal integer within 32-bit range. // and is decimal integer within 32-bit range.
if num := parseNumber(d.in); num.size > 0 { if num := parseNumber(d.in); num.size > 0 {
str := num.string(d.in)
if !num.neg && num.kind == numDec { if !num.neg && num.kind == numDec {
if _, err := strconv.ParseInt(string(d.in[:num.size]), 10, 32); err == nil { if _, err := strconv.ParseInt(str, 10, 32); err == nil {
return d.consumeToken(Name, num.size, uint8(FieldNumber)), nil return d.consumeToken(Name, num.size, uint8(FieldNumber)), nil
} }
} }
return Token{}, d.newSyntaxError("invalid field number: %s", d.in[:num.size]) return Token{}, d.newSyntaxError("invalid field number: %s", str)
} }
return Token{}, d.newSyntaxError("invalid field name: %s", errRegexp.Find(d.in)) return Token{}, d.newSyntaxError("invalid field name: %s", errId(d.in))
} }
// parseTypeName parses Any type URL or extension field name. The name is // parseTypeName parses Any type URL or extension field name. The name is
@@ -571,7 +571,7 @@ func (d *Decoder) parseScalar() (Token, error) {
return tok, nil return tok, nil
} }
return Token{}, d.newSyntaxError("invalid scalar value: %s", errRegexp.Find(d.in)) return Token{}, d.newSyntaxError("invalid scalar value: %s", errId(d.in))
} }
// parseLiteralValue parses a literal value. A literal value is used for // parseLiteralValue parses a literal value. A literal value is used for
@@ -653,8 +653,29 @@ func consume(b []byte, n int) []byte {
return b return b
} }
// Any sequence that looks like a non-delimiter (for error reporting). // errId extracts a byte sequence that looks like an invalid ID
var errRegexp = regexp.MustCompile(`^([-+._a-zA-Z0-9\/]+|.)`) // (for the purposes of error reporting).
func errId(seq []byte) []byte {
const maxLen = 32
for i := 0; i < len(seq); {
if i > maxLen {
return append(seq[:i:i], "…"...)
}
r, size := utf8.DecodeRune(seq[i:])
if r > utf8.RuneSelf || (r != '/' && isDelim(byte(r))) {
if i == 0 {
// Either the first byte is invalid UTF-8 or a
// delimiter, or the first rune is non-ASCII.
// Return it as-is.
i = size
}
return seq[:i:i]
}
i += size
}
// No delimiter found.
return seq
}
// isDelim returns true if given byte is a delimiter character. // isDelim returns true if given byte is a delimiter character.
func isDelim(c byte) bool { func isDelim(c byte) bool {

View File

@@ -15,17 +15,12 @@ func (d *Decoder) parseNumberValue() (Token, bool) {
if num.neg { if num.neg {
numAttrs |= isNegative numAttrs |= isNegative
} }
strSize := num.size
last := num.size - 1
if num.kind == numFloat && (d.in[last] == 'f' || d.in[last] == 'F') {
strSize = last
}
tok := Token{ tok := Token{
kind: Scalar, kind: Scalar,
attrs: numberValue, attrs: numberValue,
pos: len(d.orig) - len(d.in), pos: len(d.orig) - len(d.in),
raw: d.in[:num.size], raw: d.in[:num.size],
str: string(d.in[:strSize]), str: num.string(d.in),
numAttrs: numAttrs, numAttrs: numAttrs,
} }
d.consume(num.size) d.consume(num.size)
@@ -46,12 +41,35 @@ type number struct {
kind uint8 kind uint8
neg bool neg bool
size int size int
// if neg, this is the length of whitespace and comments between
// the minus sign and the rest fo the number literal
sep int
}
func (num number) string(data []byte) string {
strSize := num.size
last := num.size - 1
if num.kind == numFloat && (data[last] == 'f' || data[last] == 'F') {
strSize = last
}
if num.neg && num.sep > 0 {
// strip whitespace/comments between negative sign and the rest
strLen := strSize - num.sep
str := make([]byte, strLen)
str[0] = data[0]
copy(str[1:], data[num.sep+1:strSize])
return string(str)
}
return string(data[:strSize])
} }
// parseNumber constructs a number object from given input. It allows for the // parseNumber constructs a number object from given input. It allows for the
// following patterns: // following patterns:
//
// integer: ^-?([1-9][0-9]*|0[xX][0-9a-fA-F]+|0[0-7]*) // integer: ^-?([1-9][0-9]*|0[xX][0-9a-fA-F]+|0[0-7]*)
// float: ^-?((0|[1-9][0-9]*)?([.][0-9]*)?([eE][+-]?[0-9]+)?[fF]?) // float: ^-?((0|[1-9][0-9]*)?([.][0-9]*)?([eE][+-]?[0-9]+)?[fF]?)
//
// It also returns the number of parsed bytes for the given number, 0 if it is // It also returns the number of parsed bytes for the given number, 0 if it is
// not a number. // not a number.
func parseNumber(input []byte) number { func parseNumber(input []byte) number {
@@ -65,19 +83,22 @@ func parseNumber(input []byte) number {
} }
// Optional - // Optional -
var sep int
if s[0] == '-' { if s[0] == '-' {
neg = true neg = true
s = s[1:] s = s[1:]
size++ size++
// Consume any whitespace or comments between the
// negative sign and the rest of the number
lenBefore := len(s)
s = consume(s, 0)
sep = lenBefore - len(s)
size += sep
if len(s) == 0 { if len(s) == 0 {
return number{} return number{}
} }
} }
// C++ allows for whitespace and comments in between the negative sign and
// the rest of the number. This logic currently does not but is consistent
// with v1.
switch { switch {
case s[0] == '0': case s[0] == '0':
if len(s) > 1 { if len(s) > 1 {
@@ -114,7 +135,7 @@ func parseNumber(input []byte) number {
if len(s) > 0 && !isDelim(s[0]) { if len(s) > 0 && !isDelim(s[0]) {
return number{} return number{}
} }
return number{kind: kind, neg: neg, size: size} return number{kind: kind, neg: neg, size: size, sep: sep}
} }
} }
s = s[1:] s = s[1:]
@@ -186,5 +207,5 @@ func parseNumber(input []byte) number {
return number{} return number{}
} }
return number{kind: kind, neg: neg, size: size} return number{kind: kind, neg: neg, size: size, sep: sep}
} }

View File

@@ -24,6 +24,6 @@
// the Go implementation should as well. // the Go implementation should as well.
// //
// The text format is almost a superset of JSON except: // The text format is almost a superset of JSON except:
// * message keys are not quoted strings, but identifiers // - message keys are not quoted strings, but identifiers
// * the top-level value must be a message without the delimiters // - the top-level value must be a message without the delimiters
package text package text

View File

@@ -53,8 +53,10 @@ type encoderState struct {
// If outputASCII is true, strings will be serialized in such a way that // If outputASCII is true, strings will be serialized in such a way that
// multi-byte UTF-8 sequences are escaped. This property ensures that the // multi-byte UTF-8 sequences are escaped. This property ensures that the
// overall output is ASCII (as opposed to UTF-8). // overall output is ASCII (as opposed to UTF-8).
func NewEncoder(indent string, delims [2]byte, outputASCII bool) (*Encoder, error) { func NewEncoder(buf []byte, indent string, delims [2]byte, outputASCII bool) (*Encoder, error) {
e := &Encoder{} e := &Encoder{
encoderState: encoderState{out: buf},
}
if len(indent) > 0 { if len(indent) > 0 {
if strings.Trim(indent, " \t") != "" { if strings.Trim(indent, " \t") != "" {
return nil, errors.New("indent may only be composed of space and tab characters") return nil, errors.New("indent may only be composed of space and tab characters")
@@ -195,13 +197,13 @@ func appendFloat(out []byte, n float64, bitSize int) []byte {
// WriteInt writes out the given signed integer value. // WriteInt writes out the given signed integer value.
func (e *Encoder) WriteInt(n int64) { func (e *Encoder) WriteInt(n int64) {
e.prepareNext(scalar) e.prepareNext(scalar)
e.out = append(e.out, strconv.FormatInt(n, 10)...) e.out = strconv.AppendInt(e.out, n, 10)
} }
// WriteUint writes out the given unsigned integer value. // WriteUint writes out the given unsigned integer value.
func (e *Encoder) WriteUint(n uint64) { func (e *Encoder) WriteUint(n uint64) {
e.prepareNext(scalar) e.prepareNext(scalar)
e.out = append(e.out, strconv.FormatUint(n, 10)...) e.out = strconv.AppendUint(e.out, n, 10)
} }
// WriteLiteral writes out the given string as a literal value without quotes. // WriteLiteral writes out the given string as a literal value without quotes.
@@ -263,3 +265,8 @@ func (e *Encoder) Snapshot() encoderState {
func (e *Encoder) Reset(es encoderState) { func (e *Encoder) Reset(es encoderState) {
e.encoderState = es e.encoderState = es
} }
// AppendString appends the escaped form of the input string to b.
func AppendString(b []byte, s string) []byte {
return appendString(b, s, false)
}

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build !go1.13
// +build !go1.13 // +build !go1.13
package errors package errors

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build go1.13
// +build go1.13 // +build go1.13
package errors package errors

View File

@@ -12,8 +12,7 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/genid"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoregistry"
preg "google.golang.org/protobuf/reflect/protoregistry"
) )
// Builder construct a protoreflect.FileDescriptor from the raw descriptor. // Builder construct a protoreflect.FileDescriptor from the raw descriptor.
@@ -38,7 +37,7 @@ type Builder struct {
// TypeResolver resolves extension field types for descriptor options. // TypeResolver resolves extension field types for descriptor options.
// If nil, it uses protoregistry.GlobalTypes. // If nil, it uses protoregistry.GlobalTypes.
TypeResolver interface { TypeResolver interface {
preg.ExtensionTypeResolver protoregistry.ExtensionTypeResolver
} }
// FileRegistry is use to lookup file, enum, and message dependencies. // FileRegistry is use to lookup file, enum, and message dependencies.
@@ -46,8 +45,8 @@ type Builder struct {
// If nil, it uses protoregistry.GlobalFiles. // If nil, it uses protoregistry.GlobalFiles.
FileRegistry interface { FileRegistry interface {
FindFileByPath(string) (protoreflect.FileDescriptor, error) FindFileByPath(string) (protoreflect.FileDescriptor, error)
FindDescriptorByName(pref.FullName) (pref.Descriptor, error) FindDescriptorByName(protoreflect.FullName) (protoreflect.Descriptor, error)
RegisterFile(pref.FileDescriptor) error RegisterFile(protoreflect.FileDescriptor) error
} }
} }
@@ -55,8 +54,8 @@ type Builder struct {
// If so, it permits looking up an enum or message dependency based on the // If so, it permits looking up an enum or message dependency based on the
// sub-list and element index into filetype.Builder.DependencyIndexes. // sub-list and element index into filetype.Builder.DependencyIndexes.
type resolverByIndex interface { type resolverByIndex interface {
FindEnumByIndex(int32, int32, []Enum, []Message) pref.EnumDescriptor FindEnumByIndex(int32, int32, []Enum, []Message) protoreflect.EnumDescriptor
FindMessageByIndex(int32, int32, []Enum, []Message) pref.MessageDescriptor FindMessageByIndex(int32, int32, []Enum, []Message) protoreflect.MessageDescriptor
} }
// Indexes of each sub-list in filetype.Builder.DependencyIndexes. // Indexes of each sub-list in filetype.Builder.DependencyIndexes.
@@ -70,7 +69,7 @@ const (
// Out is the output of the Builder. // Out is the output of the Builder.
type Out struct { type Out struct {
File pref.FileDescriptor File protoreflect.FileDescriptor
// Enums is all enum descriptors in "flattened ordering". // Enums is all enum descriptors in "flattened ordering".
Enums []Enum Enums []Enum
@@ -97,10 +96,10 @@ func (db Builder) Build() (out Out) {
// Initialize resolvers and registries if unpopulated. // Initialize resolvers and registries if unpopulated.
if db.TypeResolver == nil { if db.TypeResolver == nil {
db.TypeResolver = preg.GlobalTypes db.TypeResolver = protoregistry.GlobalTypes
} }
if db.FileRegistry == nil { if db.FileRegistry == nil {
db.FileRegistry = preg.GlobalFiles db.FileRegistry = protoregistry.GlobalFiles
} }
fd := newRawFile(db) fd := newRawFile(db)

View File

@@ -17,15 +17,30 @@ import (
"google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/genid"
"google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/pragma"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
) )
// Edition is an Enum for proto2.Edition
type Edition int32
// These values align with the value of Enum in descriptor.proto which allows
// direct conversion between the proto enum and this enum.
const (
EditionUnknown Edition = 0
EditionProto2 Edition = 998
EditionProto3 Edition = 999
Edition2023 Edition = 1000
EditionUnsupported Edition = 100000
)
// The types in this file may have a suffix: // The types in this file may have a suffix:
// • L0: Contains fields common to all descriptors (except File) and // • L0: Contains fields common to all descriptors (except File) and
// must be initialized up front. // must be initialized up front.
// • L1: Contains fields specific to a descriptor and // • L1: Contains fields specific to a descriptor and
// must be initialized up front. // must be initialized up front. If the associated proto uses Editions, the
// Editions features must always be resolved. If not explicitly set, the
// appropriate default must be resolved and set.
// • L2: Contains fields that are lazily initialized when constructing // • L2: Contains fields that are lazily initialized when constructing
// from the raw file descriptor. When constructing as a literal, the L2 // from the raw file descriptor. When constructing as a literal, the L2
// fields must be initialized up front. // fields must be initialized up front.
@@ -43,45 +58,75 @@ type (
L2 *FileL2 L2 *FileL2
} }
FileL1 struct { FileL1 struct {
Syntax pref.Syntax Syntax protoreflect.Syntax
Edition Edition // Only used if Syntax == Editions
Path string Path string
Package pref.FullName Package protoreflect.FullName
Enums Enums Enums Enums
Messages Messages Messages Messages
Extensions Extensions Extensions Extensions
Services Services Services Services
EditionFeatures EditionFeatures
} }
FileL2 struct { FileL2 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Imports FileImports Imports FileImports
Locations SourceLocations Locations SourceLocations
} }
EditionFeatures struct {
// IsFieldPresence is true if field_presence is EXPLICIT
// https://protobuf.dev/editions/features/#field_presence
IsFieldPresence bool
// IsFieldPresence is true if field_presence is LEGACY_REQUIRED
// https://protobuf.dev/editions/features/#field_presence
IsLegacyRequired bool
// IsOpenEnum is true if enum_type is OPEN
// https://protobuf.dev/editions/features/#enum_type
IsOpenEnum bool
// IsPacked is true if repeated_field_encoding is PACKED
// https://protobuf.dev/editions/features/#repeated_field_encoding
IsPacked bool
// IsUTF8Validated is true if utf_validation is VERIFY
// https://protobuf.dev/editions/features/#utf8_validation
IsUTF8Validated bool
// IsDelimitedEncoded is true if message_encoding is DELIMITED
// https://protobuf.dev/editions/features/#message_encoding
IsDelimitedEncoded bool
// IsJSONCompliant is true if json_format is ALLOW
// https://protobuf.dev/editions/features/#json_format
IsJSONCompliant bool
// GenerateLegacyUnmarshalJSON determines if the plugin generates the
// UnmarshalJSON([]byte) error method for enums.
GenerateLegacyUnmarshalJSON bool
}
) )
func (fd *File) ParentFile() pref.FileDescriptor { return fd } func (fd *File) ParentFile() protoreflect.FileDescriptor { return fd }
func (fd *File) Parent() pref.Descriptor { return nil } func (fd *File) Parent() protoreflect.Descriptor { return nil }
func (fd *File) Index() int { return 0 } func (fd *File) Index() int { return 0 }
func (fd *File) Syntax() pref.Syntax { return fd.L1.Syntax } func (fd *File) Syntax() protoreflect.Syntax { return fd.L1.Syntax }
func (fd *File) Name() pref.Name { return fd.L1.Package.Name() } func (fd *File) Name() protoreflect.Name { return fd.L1.Package.Name() }
func (fd *File) FullName() pref.FullName { return fd.L1.Package } func (fd *File) FullName() protoreflect.FullName { return fd.L1.Package }
func (fd *File) IsPlaceholder() bool { return false } func (fd *File) IsPlaceholder() bool { return false }
func (fd *File) Options() pref.ProtoMessage { func (fd *File) Options() protoreflect.ProtoMessage {
if f := fd.lazyInit().Options; f != nil { if f := fd.lazyInit().Options; f != nil {
return f() return f()
} }
return descopts.File return descopts.File
} }
func (fd *File) Path() string { return fd.L1.Path } func (fd *File) Path() string { return fd.L1.Path }
func (fd *File) Package() pref.FullName { return fd.L1.Package } func (fd *File) Package() protoreflect.FullName { return fd.L1.Package }
func (fd *File) Imports() pref.FileImports { return &fd.lazyInit().Imports } func (fd *File) Imports() protoreflect.FileImports { return &fd.lazyInit().Imports }
func (fd *File) Enums() pref.EnumDescriptors { return &fd.L1.Enums } func (fd *File) Enums() protoreflect.EnumDescriptors { return &fd.L1.Enums }
func (fd *File) Messages() pref.MessageDescriptors { return &fd.L1.Messages } func (fd *File) Messages() protoreflect.MessageDescriptors { return &fd.L1.Messages }
func (fd *File) Extensions() pref.ExtensionDescriptors { return &fd.L1.Extensions } func (fd *File) Extensions() protoreflect.ExtensionDescriptors { return &fd.L1.Extensions }
func (fd *File) Services() pref.ServiceDescriptors { return &fd.L1.Services } func (fd *File) Services() protoreflect.ServiceDescriptors { return &fd.L1.Services }
func (fd *File) SourceLocations() pref.SourceLocations { return &fd.lazyInit().Locations } func (fd *File) SourceLocations() protoreflect.SourceLocations { return &fd.lazyInit().Locations }
func (fd *File) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, fd) } func (fd *File) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, fd) }
func (fd *File) ProtoType(pref.FileDescriptor) {} func (fd *File) ProtoType(protoreflect.FileDescriptor) {}
func (fd *File) ProtoInternal(pragma.DoNotImplement) {} func (fd *File) ProtoInternal(pragma.DoNotImplement) {}
func (fd *File) lazyInit() *FileL2 { func (fd *File) lazyInit() *FileL2 {
@@ -117,9 +162,11 @@ type (
} }
EnumL1 struct { EnumL1 struct {
eagerValues bool // controls whether EnumL2.Values is already populated eagerValues bool // controls whether EnumL2.Values is already populated
EditionFeatures EditionFeatures
} }
EnumL2 struct { EnumL2 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Values EnumValues Values EnumValues
ReservedNames Names ReservedNames Names
ReservedRanges EnumRanges ReservedRanges EnumRanges
@@ -130,41 +177,41 @@ type (
L1 EnumValueL1 L1 EnumValueL1
} }
EnumValueL1 struct { EnumValueL1 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Number pref.EnumNumber Number protoreflect.EnumNumber
} }
) )
func (ed *Enum) Options() pref.ProtoMessage { func (ed *Enum) Options() protoreflect.ProtoMessage {
if f := ed.lazyInit().Options; f != nil { if f := ed.lazyInit().Options; f != nil {
return f() return f()
} }
return descopts.Enum return descopts.Enum
} }
func (ed *Enum) Values() pref.EnumValueDescriptors { func (ed *Enum) Values() protoreflect.EnumValueDescriptors {
if ed.L1.eagerValues { if ed.L1.eagerValues {
return &ed.L2.Values return &ed.L2.Values
} }
return &ed.lazyInit().Values return &ed.lazyInit().Values
} }
func (ed *Enum) ReservedNames() pref.Names { return &ed.lazyInit().ReservedNames } func (ed *Enum) ReservedNames() protoreflect.Names { return &ed.lazyInit().ReservedNames }
func (ed *Enum) ReservedRanges() pref.EnumRanges { return &ed.lazyInit().ReservedRanges } func (ed *Enum) ReservedRanges() protoreflect.EnumRanges { return &ed.lazyInit().ReservedRanges }
func (ed *Enum) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, ed) } func (ed *Enum) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, ed) }
func (ed *Enum) ProtoType(pref.EnumDescriptor) {} func (ed *Enum) ProtoType(protoreflect.EnumDescriptor) {}
func (ed *Enum) lazyInit() *EnumL2 { func (ed *Enum) lazyInit() *EnumL2 {
ed.L0.ParentFile.lazyInit() // implicitly initializes L2 ed.L0.ParentFile.lazyInit() // implicitly initializes L2
return ed.L2 return ed.L2
} }
func (ed *EnumValue) Options() pref.ProtoMessage { func (ed *EnumValue) Options() protoreflect.ProtoMessage {
if f := ed.L1.Options; f != nil { if f := ed.L1.Options; f != nil {
return f() return f()
} }
return descopts.EnumValue return descopts.EnumValue
} }
func (ed *EnumValue) Number() pref.EnumNumber { return ed.L1.Number } func (ed *EnumValue) Number() protoreflect.EnumNumber { return ed.L1.Number }
func (ed *EnumValue) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, ed) } func (ed *EnumValue) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, ed) }
func (ed *EnumValue) ProtoType(pref.EnumValueDescriptor) {} func (ed *EnumValue) ProtoType(protoreflect.EnumValueDescriptor) {}
type ( type (
Message struct { Message struct {
@@ -178,16 +225,18 @@ type (
Extensions Extensions Extensions Extensions
IsMapEntry bool // promoted from google.protobuf.MessageOptions IsMapEntry bool // promoted from google.protobuf.MessageOptions
IsMessageSet bool // promoted from google.protobuf.MessageOptions IsMessageSet bool // promoted from google.protobuf.MessageOptions
EditionFeatures EditionFeatures
} }
MessageL2 struct { MessageL2 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Fields Fields Fields Fields
Oneofs Oneofs Oneofs Oneofs
ReservedNames Names ReservedNames Names
ReservedRanges FieldRanges ReservedRanges FieldRanges
RequiredNumbers FieldNumbers // must be consistent with Fields.Cardinality RequiredNumbers FieldNumbers // must be consistent with Fields.Cardinality
ExtensionRanges FieldRanges ExtensionRanges FieldRanges
ExtensionRangeOptions []func() pref.ProtoMessage // must be same length as ExtensionRanges ExtensionRangeOptions []func() protoreflect.ProtoMessage // must be same length as ExtensionRanges
} }
Field struct { Field struct {
@@ -195,10 +244,10 @@ type (
L1 FieldL1 L1 FieldL1
} }
FieldL1 struct { FieldL1 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Number pref.FieldNumber Number protoreflect.FieldNumber
Cardinality pref.Cardinality // must be consistent with Message.RequiredNumbers Cardinality protoreflect.Cardinality // must be consistent with Message.RequiredNumbers
Kind pref.Kind Kind protoreflect.Kind
StringName stringName StringName stringName
IsProto3Optional bool // promoted from google.protobuf.FieldDescriptorProto IsProto3Optional bool // promoted from google.protobuf.FieldDescriptorProto
IsWeak bool // promoted from google.protobuf.FieldOptions IsWeak bool // promoted from google.protobuf.FieldOptions
@@ -207,9 +256,11 @@ type (
HasEnforceUTF8 bool // promoted from google.protobuf.FieldOptions HasEnforceUTF8 bool // promoted from google.protobuf.FieldOptions
EnforceUTF8 bool // promoted from google.protobuf.FieldOptions EnforceUTF8 bool // promoted from google.protobuf.FieldOptions
Default defaultValue Default defaultValue
ContainingOneof pref.OneofDescriptor // must be consistent with Message.Oneofs.Fields ContainingOneof protoreflect.OneofDescriptor // must be consistent with Message.Oneofs.Fields
Enum pref.EnumDescriptor Enum protoreflect.EnumDescriptor
Message pref.MessageDescriptor Message protoreflect.MessageDescriptor
EditionFeatures EditionFeatures
} }
Oneof struct { Oneof struct {
@@ -217,34 +268,36 @@ type (
L1 OneofL1 L1 OneofL1
} }
OneofL1 struct { OneofL1 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Fields OneofFields // must be consistent with Message.Fields.ContainingOneof Fields OneofFields // must be consistent with Message.Fields.ContainingOneof
EditionFeatures EditionFeatures
} }
) )
func (md *Message) Options() pref.ProtoMessage { func (md *Message) Options() protoreflect.ProtoMessage {
if f := md.lazyInit().Options; f != nil { if f := md.lazyInit().Options; f != nil {
return f() return f()
} }
return descopts.Message return descopts.Message
} }
func (md *Message) IsMapEntry() bool { return md.L1.IsMapEntry } func (md *Message) IsMapEntry() bool { return md.L1.IsMapEntry }
func (md *Message) Fields() pref.FieldDescriptors { return &md.lazyInit().Fields } func (md *Message) Fields() protoreflect.FieldDescriptors { return &md.lazyInit().Fields }
func (md *Message) Oneofs() pref.OneofDescriptors { return &md.lazyInit().Oneofs } func (md *Message) Oneofs() protoreflect.OneofDescriptors { return &md.lazyInit().Oneofs }
func (md *Message) ReservedNames() pref.Names { return &md.lazyInit().ReservedNames } func (md *Message) ReservedNames() protoreflect.Names { return &md.lazyInit().ReservedNames }
func (md *Message) ReservedRanges() pref.FieldRanges { return &md.lazyInit().ReservedRanges } func (md *Message) ReservedRanges() protoreflect.FieldRanges { return &md.lazyInit().ReservedRanges }
func (md *Message) RequiredNumbers() pref.FieldNumbers { return &md.lazyInit().RequiredNumbers } func (md *Message) RequiredNumbers() protoreflect.FieldNumbers { return &md.lazyInit().RequiredNumbers }
func (md *Message) ExtensionRanges() pref.FieldRanges { return &md.lazyInit().ExtensionRanges } func (md *Message) ExtensionRanges() protoreflect.FieldRanges { return &md.lazyInit().ExtensionRanges }
func (md *Message) ExtensionRangeOptions(i int) pref.ProtoMessage { func (md *Message) ExtensionRangeOptions(i int) protoreflect.ProtoMessage {
if f := md.lazyInit().ExtensionRangeOptions[i]; f != nil { if f := md.lazyInit().ExtensionRangeOptions[i]; f != nil {
return f() return f()
} }
return descopts.ExtensionRange return descopts.ExtensionRange
} }
func (md *Message) Enums() pref.EnumDescriptors { return &md.L1.Enums } func (md *Message) Enums() protoreflect.EnumDescriptors { return &md.L1.Enums }
func (md *Message) Messages() pref.MessageDescriptors { return &md.L1.Messages } func (md *Message) Messages() protoreflect.MessageDescriptors { return &md.L1.Messages }
func (md *Message) Extensions() pref.ExtensionDescriptors { return &md.L1.Extensions } func (md *Message) Extensions() protoreflect.ExtensionDescriptors { return &md.L1.Extensions }
func (md *Message) ProtoType(pref.MessageDescriptor) {} func (md *Message) ProtoType(protoreflect.MessageDescriptor) {}
func (md *Message) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, md) } func (md *Message) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, md) }
func (md *Message) lazyInit() *MessageL2 { func (md *Message) lazyInit() *MessageL2 {
md.L0.ParentFile.lazyInit() // implicitly initializes L2 md.L0.ParentFile.lazyInit() // implicitly initializes L2
@@ -260,70 +313,83 @@ func (md *Message) IsMessageSet() bool {
return md.L1.IsMessageSet return md.L1.IsMessageSet
} }
func (fd *Field) Options() pref.ProtoMessage { func (fd *Field) Options() protoreflect.ProtoMessage {
if f := fd.L1.Options; f != nil { if f := fd.L1.Options; f != nil {
return f() return f()
} }
return descopts.Field return descopts.Field
} }
func (fd *Field) Number() pref.FieldNumber { return fd.L1.Number } func (fd *Field) Number() protoreflect.FieldNumber { return fd.L1.Number }
func (fd *Field) Cardinality() pref.Cardinality { return fd.L1.Cardinality } func (fd *Field) Cardinality() protoreflect.Cardinality { return fd.L1.Cardinality }
func (fd *Field) Kind() pref.Kind { return fd.L1.Kind } func (fd *Field) Kind() protoreflect.Kind {
return fd.L1.Kind
}
func (fd *Field) HasJSONName() bool { return fd.L1.StringName.hasJSON } func (fd *Field) HasJSONName() bool { return fd.L1.StringName.hasJSON }
func (fd *Field) JSONName() string { return fd.L1.StringName.getJSON(fd) } func (fd *Field) JSONName() string { return fd.L1.StringName.getJSON(fd) }
func (fd *Field) TextName() string { return fd.L1.StringName.getText(fd) } func (fd *Field) TextName() string { return fd.L1.StringName.getText(fd) }
func (fd *Field) HasPresence() bool { func (fd *Field) HasPresence() bool {
return fd.L1.Cardinality != pref.Repeated && (fd.L0.ParentFile.L1.Syntax == pref.Proto2 || fd.L1.Message != nil || fd.L1.ContainingOneof != nil) if fd.L1.Cardinality == protoreflect.Repeated {
return false
}
explicitFieldPresence := fd.Syntax() == protoreflect.Editions && fd.L1.EditionFeatures.IsFieldPresence
return fd.Syntax() == protoreflect.Proto2 || explicitFieldPresence || fd.L1.Message != nil || fd.L1.ContainingOneof != nil
} }
func (fd *Field) HasOptionalKeyword() bool { func (fd *Field) HasOptionalKeyword() bool {
return (fd.L0.ParentFile.L1.Syntax == pref.Proto2 && fd.L1.Cardinality == pref.Optional && fd.L1.ContainingOneof == nil) || fd.L1.IsProto3Optional return (fd.L0.ParentFile.L1.Syntax == protoreflect.Proto2 && fd.L1.Cardinality == protoreflect.Optional && fd.L1.ContainingOneof == nil) || fd.L1.IsProto3Optional
} }
func (fd *Field) IsPacked() bool { func (fd *Field) IsPacked() bool {
if !fd.L1.HasPacked && fd.L0.ParentFile.L1.Syntax != pref.Proto2 && fd.L1.Cardinality == pref.Repeated { if fd.L1.Cardinality != protoreflect.Repeated {
switch fd.L1.Kind { return false
case pref.StringKind, pref.BytesKind, pref.MessageKind, pref.GroupKind:
default:
return true
} }
switch fd.L1.Kind {
case protoreflect.StringKind, protoreflect.BytesKind, protoreflect.MessageKind, protoreflect.GroupKind:
return false
}
if fd.L0.ParentFile.L1.Syntax == protoreflect.Editions {
return fd.L1.EditionFeatures.IsPacked
}
if fd.L0.ParentFile.L1.Syntax == protoreflect.Proto3 {
// proto3 repeated fields are packed by default.
return !fd.L1.HasPacked || fd.L1.IsPacked
} }
return fd.L1.IsPacked return fd.L1.IsPacked
} }
func (fd *Field) IsExtension() bool { return false } func (fd *Field) IsExtension() bool { return false }
func (fd *Field) IsWeak() bool { return fd.L1.IsWeak } func (fd *Field) IsWeak() bool { return fd.L1.IsWeak }
func (fd *Field) IsList() bool { return fd.Cardinality() == pref.Repeated && !fd.IsMap() } func (fd *Field) IsList() bool { return fd.Cardinality() == protoreflect.Repeated && !fd.IsMap() }
func (fd *Field) IsMap() bool { return fd.Message() != nil && fd.Message().IsMapEntry() } func (fd *Field) IsMap() bool { return fd.Message() != nil && fd.Message().IsMapEntry() }
func (fd *Field) MapKey() pref.FieldDescriptor { func (fd *Field) MapKey() protoreflect.FieldDescriptor {
if !fd.IsMap() { if !fd.IsMap() {
return nil return nil
} }
return fd.Message().Fields().ByNumber(genid.MapEntry_Key_field_number) return fd.Message().Fields().ByNumber(genid.MapEntry_Key_field_number)
} }
func (fd *Field) MapValue() pref.FieldDescriptor { func (fd *Field) MapValue() protoreflect.FieldDescriptor {
if !fd.IsMap() { if !fd.IsMap() {
return nil return nil
} }
return fd.Message().Fields().ByNumber(genid.MapEntry_Value_field_number) return fd.Message().Fields().ByNumber(genid.MapEntry_Value_field_number)
} }
func (fd *Field) HasDefault() bool { return fd.L1.Default.has } func (fd *Field) HasDefault() bool { return fd.L1.Default.has }
func (fd *Field) Default() pref.Value { return fd.L1.Default.get(fd) } func (fd *Field) Default() protoreflect.Value { return fd.L1.Default.get(fd) }
func (fd *Field) DefaultEnumValue() pref.EnumValueDescriptor { return fd.L1.Default.enum } func (fd *Field) DefaultEnumValue() protoreflect.EnumValueDescriptor { return fd.L1.Default.enum }
func (fd *Field) ContainingOneof() pref.OneofDescriptor { return fd.L1.ContainingOneof } func (fd *Field) ContainingOneof() protoreflect.OneofDescriptor { return fd.L1.ContainingOneof }
func (fd *Field) ContainingMessage() pref.MessageDescriptor { func (fd *Field) ContainingMessage() protoreflect.MessageDescriptor {
return fd.L0.Parent.(pref.MessageDescriptor) return fd.L0.Parent.(protoreflect.MessageDescriptor)
} }
func (fd *Field) Enum() pref.EnumDescriptor { func (fd *Field) Enum() protoreflect.EnumDescriptor {
return fd.L1.Enum return fd.L1.Enum
} }
func (fd *Field) Message() pref.MessageDescriptor { func (fd *Field) Message() protoreflect.MessageDescriptor {
if fd.L1.IsWeak { if fd.L1.IsWeak {
if d, _ := protoregistry.GlobalFiles.FindDescriptorByName(fd.L1.Message.FullName()); d != nil { if d, _ := protoregistry.GlobalFiles.FindDescriptorByName(fd.L1.Message.FullName()); d != nil {
return d.(pref.MessageDescriptor) return d.(protoreflect.MessageDescriptor)
} }
} }
return fd.L1.Message return fd.L1.Message
} }
func (fd *Field) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, fd) } func (fd *Field) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, fd) }
func (fd *Field) ProtoType(pref.FieldDescriptor) {} func (fd *Field) ProtoType(protoreflect.FieldDescriptor) {}
// EnforceUTF8 is a pseudo-internal API to determine whether to enforce UTF-8 // EnforceUTF8 is a pseudo-internal API to determine whether to enforce UTF-8
// validation for the string field. This exists for Google-internal use only // validation for the string field. This exists for Google-internal use only
@@ -333,24 +399,27 @@ func (fd *Field) ProtoType(pref.FieldDescriptor) {}
// WARNING: This method is exempt from the compatibility promise and may be // WARNING: This method is exempt from the compatibility promise and may be
// removed in the future without warning. // removed in the future without warning.
func (fd *Field) EnforceUTF8() bool { func (fd *Field) EnforceUTF8() bool {
if fd.L0.ParentFile.L1.Syntax == protoreflect.Editions {
return fd.L1.EditionFeatures.IsUTF8Validated
}
if fd.L1.HasEnforceUTF8 { if fd.L1.HasEnforceUTF8 {
return fd.L1.EnforceUTF8 return fd.L1.EnforceUTF8
} }
return fd.L0.ParentFile.L1.Syntax == pref.Proto3 return fd.L0.ParentFile.L1.Syntax == protoreflect.Proto3
} }
func (od *Oneof) IsSynthetic() bool { func (od *Oneof) IsSynthetic() bool {
return od.L0.ParentFile.L1.Syntax == pref.Proto3 && len(od.L1.Fields.List) == 1 && od.L1.Fields.List[0].HasOptionalKeyword() return od.L0.ParentFile.L1.Syntax == protoreflect.Proto3 && len(od.L1.Fields.List) == 1 && od.L1.Fields.List[0].HasOptionalKeyword()
} }
func (od *Oneof) Options() pref.ProtoMessage { func (od *Oneof) Options() protoreflect.ProtoMessage {
if f := od.L1.Options; f != nil { if f := od.L1.Options; f != nil {
return f() return f()
} }
return descopts.Oneof return descopts.Oneof
} }
func (od *Oneof) Fields() pref.FieldDescriptors { return &od.L1.Fields } func (od *Oneof) Fields() protoreflect.FieldDescriptors { return &od.L1.Fields }
func (od *Oneof) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, od) } func (od *Oneof) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, od) }
func (od *Oneof) ProtoType(pref.OneofDescriptor) {} func (od *Oneof) ProtoType(protoreflect.OneofDescriptor) {}
type ( type (
Extension struct { Extension struct {
@@ -359,54 +428,57 @@ type (
L2 *ExtensionL2 // protected by fileDesc.once L2 *ExtensionL2 // protected by fileDesc.once
} }
ExtensionL1 struct { ExtensionL1 struct {
Number pref.FieldNumber Number protoreflect.FieldNumber
Extendee pref.MessageDescriptor Extendee protoreflect.MessageDescriptor
Cardinality pref.Cardinality Cardinality protoreflect.Cardinality
Kind pref.Kind Kind protoreflect.Kind
EditionFeatures EditionFeatures
} }
ExtensionL2 struct { ExtensionL2 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
StringName stringName StringName stringName
IsProto3Optional bool // promoted from google.protobuf.FieldDescriptorProto IsProto3Optional bool // promoted from google.protobuf.FieldDescriptorProto
IsPacked bool // promoted from google.protobuf.FieldOptions IsPacked bool // promoted from google.protobuf.FieldOptions
Default defaultValue Default defaultValue
Enum pref.EnumDescriptor Enum protoreflect.EnumDescriptor
Message pref.MessageDescriptor Message protoreflect.MessageDescriptor
} }
) )
func (xd *Extension) Options() pref.ProtoMessage { func (xd *Extension) Options() protoreflect.ProtoMessage {
if f := xd.lazyInit().Options; f != nil { if f := xd.lazyInit().Options; f != nil {
return f() return f()
} }
return descopts.Field return descopts.Field
} }
func (xd *Extension) Number() pref.FieldNumber { return xd.L1.Number } func (xd *Extension) Number() protoreflect.FieldNumber { return xd.L1.Number }
func (xd *Extension) Cardinality() pref.Cardinality { return xd.L1.Cardinality } func (xd *Extension) Cardinality() protoreflect.Cardinality { return xd.L1.Cardinality }
func (xd *Extension) Kind() pref.Kind { return xd.L1.Kind } func (xd *Extension) Kind() protoreflect.Kind { return xd.L1.Kind }
func (xd *Extension) HasJSONName() bool { return xd.lazyInit().StringName.hasJSON } func (xd *Extension) HasJSONName() bool { return xd.lazyInit().StringName.hasJSON }
func (xd *Extension) JSONName() string { return xd.lazyInit().StringName.getJSON(xd) } func (xd *Extension) JSONName() string { return xd.lazyInit().StringName.getJSON(xd) }
func (xd *Extension) TextName() string { return xd.lazyInit().StringName.getText(xd) } func (xd *Extension) TextName() string { return xd.lazyInit().StringName.getText(xd) }
func (xd *Extension) HasPresence() bool { return xd.L1.Cardinality != pref.Repeated } func (xd *Extension) HasPresence() bool { return xd.L1.Cardinality != protoreflect.Repeated }
func (xd *Extension) HasOptionalKeyword() bool { func (xd *Extension) HasOptionalKeyword() bool {
return (xd.L0.ParentFile.L1.Syntax == pref.Proto2 && xd.L1.Cardinality == pref.Optional) || xd.lazyInit().IsProto3Optional return (xd.L0.ParentFile.L1.Syntax == protoreflect.Proto2 && xd.L1.Cardinality == protoreflect.Optional) || xd.lazyInit().IsProto3Optional
} }
func (xd *Extension) IsPacked() bool { return xd.lazyInit().IsPacked } func (xd *Extension) IsPacked() bool { return xd.lazyInit().IsPacked }
func (xd *Extension) IsExtension() bool { return true } func (xd *Extension) IsExtension() bool { return true }
func (xd *Extension) IsWeak() bool { return false } func (xd *Extension) IsWeak() bool { return false }
func (xd *Extension) IsList() bool { return xd.Cardinality() == pref.Repeated } func (xd *Extension) IsList() bool { return xd.Cardinality() == protoreflect.Repeated }
func (xd *Extension) IsMap() bool { return false } func (xd *Extension) IsMap() bool { return false }
func (xd *Extension) MapKey() pref.FieldDescriptor { return nil } func (xd *Extension) MapKey() protoreflect.FieldDescriptor { return nil }
func (xd *Extension) MapValue() pref.FieldDescriptor { return nil } func (xd *Extension) MapValue() protoreflect.FieldDescriptor { return nil }
func (xd *Extension) HasDefault() bool { return xd.lazyInit().Default.has } func (xd *Extension) HasDefault() bool { return xd.lazyInit().Default.has }
func (xd *Extension) Default() pref.Value { return xd.lazyInit().Default.get(xd) } func (xd *Extension) Default() protoreflect.Value { return xd.lazyInit().Default.get(xd) }
func (xd *Extension) DefaultEnumValue() pref.EnumValueDescriptor { return xd.lazyInit().Default.enum } func (xd *Extension) DefaultEnumValue() protoreflect.EnumValueDescriptor {
func (xd *Extension) ContainingOneof() pref.OneofDescriptor { return nil } return xd.lazyInit().Default.enum
func (xd *Extension) ContainingMessage() pref.MessageDescriptor { return xd.L1.Extendee } }
func (xd *Extension) Enum() pref.EnumDescriptor { return xd.lazyInit().Enum } func (xd *Extension) ContainingOneof() protoreflect.OneofDescriptor { return nil }
func (xd *Extension) Message() pref.MessageDescriptor { return xd.lazyInit().Message } func (xd *Extension) ContainingMessage() protoreflect.MessageDescriptor { return xd.L1.Extendee }
func (xd *Extension) Enum() protoreflect.EnumDescriptor { return xd.lazyInit().Enum }
func (xd *Extension) Message() protoreflect.MessageDescriptor { return xd.lazyInit().Message }
func (xd *Extension) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, xd) } func (xd *Extension) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, xd) }
func (xd *Extension) ProtoType(pref.FieldDescriptor) {} func (xd *Extension) ProtoType(protoreflect.FieldDescriptor) {}
func (xd *Extension) ProtoInternal(pragma.DoNotImplement) {} func (xd *Extension) ProtoInternal(pragma.DoNotImplement) {}
func (xd *Extension) lazyInit() *ExtensionL2 { func (xd *Extension) lazyInit() *ExtensionL2 {
xd.L0.ParentFile.lazyInit() // implicitly initializes L2 xd.L0.ParentFile.lazyInit() // implicitly initializes L2
@@ -421,7 +493,7 @@ type (
} }
ServiceL1 struct{} ServiceL1 struct{}
ServiceL2 struct { ServiceL2 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Methods Methods Methods Methods
} }
@@ -430,48 +502,48 @@ type (
L1 MethodL1 L1 MethodL1
} }
MethodL1 struct { MethodL1 struct {
Options func() pref.ProtoMessage Options func() protoreflect.ProtoMessage
Input pref.MessageDescriptor Input protoreflect.MessageDescriptor
Output pref.MessageDescriptor Output protoreflect.MessageDescriptor
IsStreamingClient bool IsStreamingClient bool
IsStreamingServer bool IsStreamingServer bool
} }
) )
func (sd *Service) Options() pref.ProtoMessage { func (sd *Service) Options() protoreflect.ProtoMessage {
if f := sd.lazyInit().Options; f != nil { if f := sd.lazyInit().Options; f != nil {
return f() return f()
} }
return descopts.Service return descopts.Service
} }
func (sd *Service) Methods() pref.MethodDescriptors { return &sd.lazyInit().Methods } func (sd *Service) Methods() protoreflect.MethodDescriptors { return &sd.lazyInit().Methods }
func (sd *Service) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, sd) } func (sd *Service) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, sd) }
func (sd *Service) ProtoType(pref.ServiceDescriptor) {} func (sd *Service) ProtoType(protoreflect.ServiceDescriptor) {}
func (sd *Service) ProtoInternal(pragma.DoNotImplement) {} func (sd *Service) ProtoInternal(pragma.DoNotImplement) {}
func (sd *Service) lazyInit() *ServiceL2 { func (sd *Service) lazyInit() *ServiceL2 {
sd.L0.ParentFile.lazyInit() // implicitly initializes L2 sd.L0.ParentFile.lazyInit() // implicitly initializes L2
return sd.L2 return sd.L2
} }
func (md *Method) Options() pref.ProtoMessage { func (md *Method) Options() protoreflect.ProtoMessage {
if f := md.L1.Options; f != nil { if f := md.L1.Options; f != nil {
return f() return f()
} }
return descopts.Method return descopts.Method
} }
func (md *Method) Input() pref.MessageDescriptor { return md.L1.Input } func (md *Method) Input() protoreflect.MessageDescriptor { return md.L1.Input }
func (md *Method) Output() pref.MessageDescriptor { return md.L1.Output } func (md *Method) Output() protoreflect.MessageDescriptor { return md.L1.Output }
func (md *Method) IsStreamingClient() bool { return md.L1.IsStreamingClient } func (md *Method) IsStreamingClient() bool { return md.L1.IsStreamingClient }
func (md *Method) IsStreamingServer() bool { return md.L1.IsStreamingServer } func (md *Method) IsStreamingServer() bool { return md.L1.IsStreamingServer }
func (md *Method) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, md) } func (md *Method) Format(s fmt.State, r rune) { descfmt.FormatDesc(s, r, md) }
func (md *Method) ProtoType(pref.MethodDescriptor) {} func (md *Method) ProtoType(protoreflect.MethodDescriptor) {}
func (md *Method) ProtoInternal(pragma.DoNotImplement) {} func (md *Method) ProtoInternal(pragma.DoNotImplement) {}
// Surrogate files are can be used to create standalone descriptors // Surrogate files are can be used to create standalone descriptors
// where the syntax is only information derived from the parent file. // where the syntax is only information derived from the parent file.
var ( var (
SurrogateProto2 = &File{L1: FileL1{Syntax: pref.Proto2}, L2: &FileL2{}} SurrogateProto2 = &File{L1: FileL1{Syntax: protoreflect.Proto2}, L2: &FileL2{}}
SurrogateProto3 = &File{L1: FileL1{Syntax: pref.Proto3}, L2: &FileL2{}} SurrogateProto3 = &File{L1: FileL1{Syntax: protoreflect.Proto3}, L2: &FileL2{}}
) )
type ( type (
@@ -479,24 +551,24 @@ type (
L0 BaseL0 L0 BaseL0
} }
BaseL0 struct { BaseL0 struct {
FullName pref.FullName // must be populated FullName protoreflect.FullName // must be populated
ParentFile *File // must be populated ParentFile *File // must be populated
Parent pref.Descriptor Parent protoreflect.Descriptor
Index int Index int
} }
) )
func (d *Base) Name() pref.Name { return d.L0.FullName.Name() } func (d *Base) Name() protoreflect.Name { return d.L0.FullName.Name() }
func (d *Base) FullName() pref.FullName { return d.L0.FullName } func (d *Base) FullName() protoreflect.FullName { return d.L0.FullName }
func (d *Base) ParentFile() pref.FileDescriptor { func (d *Base) ParentFile() protoreflect.FileDescriptor {
if d.L0.ParentFile == SurrogateProto2 || d.L0.ParentFile == SurrogateProto3 { if d.L0.ParentFile == SurrogateProto2 || d.L0.ParentFile == SurrogateProto3 {
return nil // surrogate files are not real parents return nil // surrogate files are not real parents
} }
return d.L0.ParentFile return d.L0.ParentFile
} }
func (d *Base) Parent() pref.Descriptor { return d.L0.Parent } func (d *Base) Parent() protoreflect.Descriptor { return d.L0.Parent }
func (d *Base) Index() int { return d.L0.Index } func (d *Base) Index() int { return d.L0.Index }
func (d *Base) Syntax() pref.Syntax { return d.L0.ParentFile.Syntax() } func (d *Base) Syntax() protoreflect.Syntax { return d.L0.ParentFile.Syntax() }
func (d *Base) IsPlaceholder() bool { return false } func (d *Base) IsPlaceholder() bool { return false }
func (d *Base) ProtoInternal(pragma.DoNotImplement) {} func (d *Base) ProtoInternal(pragma.DoNotImplement) {}
@@ -513,7 +585,7 @@ func (s *stringName) InitJSON(name string) {
s.nameJSON = name s.nameJSON = name
} }
func (s *stringName) lazyInit(fd pref.FieldDescriptor) *stringName { func (s *stringName) lazyInit(fd protoreflect.FieldDescriptor) *stringName {
s.once.Do(func() { s.once.Do(func() {
if fd.IsExtension() { if fd.IsExtension() {
// For extensions, JSON and text are formatted the same way. // For extensions, JSON and text are formatted the same way.
@@ -533,7 +605,7 @@ func (s *stringName) lazyInit(fd pref.FieldDescriptor) *stringName {
// Format the text name. // Format the text name.
s.nameText = string(fd.Name()) s.nameText = string(fd.Name())
if fd.Kind() == pref.GroupKind { if fd.Kind() == protoreflect.GroupKind {
s.nameText = string(fd.Message().Name()) s.nameText = string(fd.Message().Name())
} }
} }
@@ -541,10 +613,10 @@ func (s *stringName) lazyInit(fd pref.FieldDescriptor) *stringName {
return s return s
} }
func (s *stringName) getJSON(fd pref.FieldDescriptor) string { return s.lazyInit(fd).nameJSON } func (s *stringName) getJSON(fd protoreflect.FieldDescriptor) string { return s.lazyInit(fd).nameJSON }
func (s *stringName) getText(fd pref.FieldDescriptor) string { return s.lazyInit(fd).nameText } func (s *stringName) getText(fd protoreflect.FieldDescriptor) string { return s.lazyInit(fd).nameText }
func DefaultValue(v pref.Value, ev pref.EnumValueDescriptor) defaultValue { func DefaultValue(v protoreflect.Value, ev protoreflect.EnumValueDescriptor) defaultValue {
dv := defaultValue{has: v.IsValid(), val: v, enum: ev} dv := defaultValue{has: v.IsValid(), val: v, enum: ev}
if b, ok := v.Interface().([]byte); ok { if b, ok := v.Interface().([]byte); ok {
// Store a copy of the default bytes, so that we can detect // Store a copy of the default bytes, so that we can detect
@@ -554,9 +626,9 @@ func DefaultValue(v pref.Value, ev pref.EnumValueDescriptor) defaultValue {
return dv return dv
} }
func unmarshalDefault(b []byte, k pref.Kind, pf *File, ed pref.EnumDescriptor) defaultValue { func unmarshalDefault(b []byte, k protoreflect.Kind, pf *File, ed protoreflect.EnumDescriptor) defaultValue {
var evs pref.EnumValueDescriptors var evs protoreflect.EnumValueDescriptors
if k == pref.EnumKind { if k == protoreflect.EnumKind {
// If the enum is declared within the same file, be careful not to // If the enum is declared within the same file, be careful not to
// blindly call the Values method, lest we bind ourselves in a deadlock. // blindly call the Values method, lest we bind ourselves in a deadlock.
if e, ok := ed.(*Enum); ok && e.L0.ParentFile == pf { if e, ok := ed.(*Enum); ok && e.L0.ParentFile == pf {
@@ -567,9 +639,9 @@ func unmarshalDefault(b []byte, k pref.Kind, pf *File, ed pref.EnumDescriptor) d
// If we are unable to resolve the enum dependency, use a placeholder // If we are unable to resolve the enum dependency, use a placeholder
// enum value since we will not be able to parse the default value. // enum value since we will not be able to parse the default value.
if ed.IsPlaceholder() && pref.Name(b).IsValid() { if ed.IsPlaceholder() && protoreflect.Name(b).IsValid() {
v := pref.ValueOfEnum(0) v := protoreflect.ValueOfEnum(0)
ev := PlaceholderEnumValue(ed.FullName().Parent().Append(pref.Name(b))) ev := PlaceholderEnumValue(ed.FullName().Parent().Append(protoreflect.Name(b)))
return DefaultValue(v, ev) return DefaultValue(v, ev)
} }
} }
@@ -583,41 +655,41 @@ func unmarshalDefault(b []byte, k pref.Kind, pf *File, ed pref.EnumDescriptor) d
type defaultValue struct { type defaultValue struct {
has bool has bool
val pref.Value val protoreflect.Value
enum pref.EnumValueDescriptor enum protoreflect.EnumValueDescriptor
bytes []byte bytes []byte
} }
func (dv *defaultValue) get(fd pref.FieldDescriptor) pref.Value { func (dv *defaultValue) get(fd protoreflect.FieldDescriptor) protoreflect.Value {
// Return the zero value as the default if unpopulated. // Return the zero value as the default if unpopulated.
if !dv.has { if !dv.has {
if fd.Cardinality() == pref.Repeated { if fd.Cardinality() == protoreflect.Repeated {
return pref.Value{} return protoreflect.Value{}
} }
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
return pref.ValueOfBool(false) return protoreflect.ValueOfBool(false)
case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind: case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind:
return pref.ValueOfInt32(0) return protoreflect.ValueOfInt32(0)
case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind: case protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
return pref.ValueOfInt64(0) return protoreflect.ValueOfInt64(0)
case pref.Uint32Kind, pref.Fixed32Kind: case protoreflect.Uint32Kind, protoreflect.Fixed32Kind:
return pref.ValueOfUint32(0) return protoreflect.ValueOfUint32(0)
case pref.Uint64Kind, pref.Fixed64Kind: case protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
return pref.ValueOfUint64(0) return protoreflect.ValueOfUint64(0)
case pref.FloatKind: case protoreflect.FloatKind:
return pref.ValueOfFloat32(0) return protoreflect.ValueOfFloat32(0)
case pref.DoubleKind: case protoreflect.DoubleKind:
return pref.ValueOfFloat64(0) return protoreflect.ValueOfFloat64(0)
case pref.StringKind: case protoreflect.StringKind:
return pref.ValueOfString("") return protoreflect.ValueOfString("")
case pref.BytesKind: case protoreflect.BytesKind:
return pref.ValueOfBytes(nil) return protoreflect.ValueOfBytes(nil)
case pref.EnumKind: case protoreflect.EnumKind:
if evs := fd.Enum().Values(); evs.Len() > 0 { if evs := fd.Enum().Values(); evs.Len() > 0 {
return pref.ValueOfEnum(evs.Get(0).Number()) return protoreflect.ValueOfEnum(evs.Get(0).Number())
} }
return pref.ValueOfEnum(0) return protoreflect.ValueOfEnum(0)
} }
} }

View File

@@ -5,12 +5,13 @@
package filedesc package filedesc
import ( import (
"fmt"
"sync" "sync"
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/genid"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
// fileRaw is a data struct used when initializing a file descriptor from // fileRaw is a data struct used when initializing a file descriptor from
@@ -95,9 +96,10 @@ func (fd *File) unmarshalSeed(b []byte) {
sb := getBuilder() sb := getBuilder()
defer putBuilder(sb) defer putBuilder(sb)
var prevField pref.FieldNumber var prevField protoreflect.FieldNumber
var numEnums, numMessages, numExtensions, numServices int var numEnums, numMessages, numExtensions, numServices int
var posEnums, posMessages, posExtensions, posServices int var posEnums, posMessages, posExtensions, posServices int
var options []byte
b0 := b b0 := b
for len(b) > 0 { for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b) num, typ, n := protowire.ConsumeTag(b)
@@ -110,16 +112,20 @@ func (fd *File) unmarshalSeed(b []byte) {
case genid.FileDescriptorProto_Syntax_field_number: case genid.FileDescriptorProto_Syntax_field_number:
switch string(v) { switch string(v) {
case "proto2": case "proto2":
fd.L1.Syntax = pref.Proto2 fd.L1.Syntax = protoreflect.Proto2
case "proto3": case "proto3":
fd.L1.Syntax = pref.Proto3 fd.L1.Syntax = protoreflect.Proto3
case "editions":
fd.L1.Syntax = protoreflect.Editions
default: default:
panic("invalid syntax") panic("invalid syntax")
} }
case genid.FileDescriptorProto_Name_field_number: case genid.FileDescriptorProto_Name_field_number:
fd.L1.Path = sb.MakeString(v) fd.L1.Path = sb.MakeString(v)
case genid.FileDescriptorProto_Package_field_number: case genid.FileDescriptorProto_Package_field_number:
fd.L1.Package = pref.FullName(sb.MakeString(v)) fd.L1.Package = protoreflect.FullName(sb.MakeString(v))
case genid.FileDescriptorProto_Options_field_number:
options = v
case genid.FileDescriptorProto_EnumType_field_number: case genid.FileDescriptorProto_EnumType_field_number:
if prevField != genid.FileDescriptorProto_EnumType_field_number { if prevField != genid.FileDescriptorProto_EnumType_field_number {
if numEnums > 0 { if numEnums > 0 {
@@ -154,6 +160,13 @@ func (fd *File) unmarshalSeed(b []byte) {
numServices++ numServices++
} }
prevField = num prevField = num
case protowire.VarintType:
v, m := protowire.ConsumeVarint(b)
b = b[m:]
switch num {
case genid.FileDescriptorProto_Edition_field_number:
fd.L1.Edition = Edition(v)
}
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
b = b[m:] b = b[m:]
@@ -163,7 +176,16 @@ func (fd *File) unmarshalSeed(b []byte) {
// If syntax is missing, it is assumed to be proto2. // If syntax is missing, it is assumed to be proto2.
if fd.L1.Syntax == 0 { if fd.L1.Syntax == 0 {
fd.L1.Syntax = pref.Proto2 fd.L1.Syntax = protoreflect.Proto2
}
if fd.L1.Syntax == protoreflect.Editions {
fd.L1.EditionFeatures = getFeaturesFor(fd.L1.Edition)
}
// Parse editions features from options if any
if options != nil {
fd.unmarshalSeedOptions(options)
} }
// Must allocate all declarations before parsing each descriptor type // Must allocate all declarations before parsing each descriptor type
@@ -219,7 +241,29 @@ func (fd *File) unmarshalSeed(b []byte) {
} }
} }
func (ed *Enum) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (fd *File) unmarshalSeedOptions(b []byte) {
for b := b; len(b) > 0; {
num, typ, n := protowire.ConsumeTag(b)
b = b[n:]
switch typ {
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.FileOptions_Features_field_number:
if fd.Syntax() != protoreflect.Editions {
panic(fmt.Sprintf("invalid descriptor: using edition features in a proto with syntax %s", fd.Syntax()))
}
fd.L1.EditionFeatures = unmarshalFeatureSet(v, fd.L1.EditionFeatures)
}
default:
m := protowire.ConsumeFieldValue(num, typ, b)
b = b[m:]
}
}
}
func (ed *Enum) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
ed.L0.ParentFile = pf ed.L0.ParentFile = pf
ed.L0.Parent = pd ed.L0.Parent = pd
ed.L0.Index = i ed.L0.Index = i
@@ -271,12 +315,13 @@ func (ed *Enum) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref.Desc
} }
} }
func (md *Message) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (md *Message) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
md.L0.ParentFile = pf md.L0.ParentFile = pf
md.L0.Parent = pd md.L0.Parent = pd
md.L0.Index = i md.L0.Index = i
md.L1.EditionFeatures = featuresFromParentDesc(md.Parent())
var prevField pref.FieldNumber var prevField protoreflect.FieldNumber
var numEnums, numMessages, numExtensions int var numEnums, numMessages, numExtensions int
var posEnums, posMessages, posExtensions int var posEnums, posMessages, posExtensions int
b0 := b b0 := b
@@ -380,6 +425,13 @@ func (md *Message) unmarshalSeedOptions(b []byte) {
case genid.MessageOptions_MessageSetWireFormat_field_number: case genid.MessageOptions_MessageSetWireFormat_field_number:
md.L1.IsMessageSet = protowire.DecodeBool(v) md.L1.IsMessageSet = protowire.DecodeBool(v)
} }
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.MessageOptions_Features_field_number:
md.L1.EditionFeatures = unmarshalFeatureSet(v, md.L1.EditionFeatures)
}
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
b = b[m:] b = b[m:]
@@ -387,7 +439,7 @@ func (md *Message) unmarshalSeedOptions(b []byte) {
} }
} }
func (xd *Extension) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (xd *Extension) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
xd.L0.ParentFile = pf xd.L0.ParentFile = pf
xd.L0.Parent = pd xd.L0.Parent = pd
xd.L0.Index = i xd.L0.Index = i
@@ -401,11 +453,11 @@ func (xd *Extension) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref
b = b[m:] b = b[m:]
switch num { switch num {
case genid.FieldDescriptorProto_Number_field_number: case genid.FieldDescriptorProto_Number_field_number:
xd.L1.Number = pref.FieldNumber(v) xd.L1.Number = protoreflect.FieldNumber(v)
case genid.FieldDescriptorProto_Label_field_number: case genid.FieldDescriptorProto_Label_field_number:
xd.L1.Cardinality = pref.Cardinality(v) xd.L1.Cardinality = protoreflect.Cardinality(v)
case genid.FieldDescriptorProto_Type_field_number: case genid.FieldDescriptorProto_Type_field_number:
xd.L1.Kind = pref.Kind(v) xd.L1.Kind = protoreflect.Kind(v)
} }
case protowire.BytesType: case protowire.BytesType:
v, m := protowire.ConsumeBytes(b) v, m := protowire.ConsumeBytes(b)
@@ -423,7 +475,7 @@ func (xd *Extension) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref
} }
} }
func (sd *Service) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (sd *Service) unmarshalSeed(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
sd.L0.ParentFile = pf sd.L0.ParentFile = pf
sd.L0.Parent = pd sd.L0.Parent = pd
sd.L0.Index = i sd.L0.Index = i
@@ -459,13 +511,13 @@ func putBuilder(b *strs.Builder) {
// makeFullName converts b to a protoreflect.FullName, // makeFullName converts b to a protoreflect.FullName,
// where b must start with a leading dot. // where b must start with a leading dot.
func makeFullName(sb *strs.Builder, b []byte) pref.FullName { func makeFullName(sb *strs.Builder, b []byte) protoreflect.FullName {
if len(b) == 0 || b[0] != '.' { if len(b) == 0 || b[0] != '.' {
panic("name reference must be fully qualified") panic("name reference must be fully qualified")
} }
return pref.FullName(sb.MakeString(b[1:])) return protoreflect.FullName(sb.MakeString(b[1:]))
} }
func appendFullName(sb *strs.Builder, prefix pref.FullName, suffix []byte) pref.FullName { func appendFullName(sb *strs.Builder, prefix protoreflect.FullName, suffix []byte) protoreflect.FullName {
return sb.AppendFullName(prefix, pref.Name(strs.UnsafeString(suffix))) return sb.AppendFullName(prefix, protoreflect.Name(strs.UnsafeString(suffix)))
} }

View File

@@ -13,7 +13,7 @@ import (
"google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/genid"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
func (fd *File) lazyRawInit() { func (fd *File) lazyRawInit() {
@@ -39,10 +39,10 @@ func (file *File) resolveMessages() {
// Resolve message field dependency. // Resolve message field dependency.
switch fd.L1.Kind { switch fd.L1.Kind {
case pref.EnumKind: case protoreflect.EnumKind:
fd.L1.Enum = file.resolveEnumDependency(fd.L1.Enum, listFieldDeps, depIdx) fd.L1.Enum = file.resolveEnumDependency(fd.L1.Enum, listFieldDeps, depIdx)
depIdx++ depIdx++
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
fd.L1.Message = file.resolveMessageDependency(fd.L1.Message, listFieldDeps, depIdx) fd.L1.Message = file.resolveMessageDependency(fd.L1.Message, listFieldDeps, depIdx)
depIdx++ depIdx++
} }
@@ -62,10 +62,10 @@ func (file *File) resolveExtensions() {
// Resolve extension field dependency. // Resolve extension field dependency.
switch xd.L1.Kind { switch xd.L1.Kind {
case pref.EnumKind: case protoreflect.EnumKind:
xd.L2.Enum = file.resolveEnumDependency(xd.L2.Enum, listExtDeps, depIdx) xd.L2.Enum = file.resolveEnumDependency(xd.L2.Enum, listExtDeps, depIdx)
depIdx++ depIdx++
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
xd.L2.Message = file.resolveMessageDependency(xd.L2.Message, listExtDeps, depIdx) xd.L2.Message = file.resolveMessageDependency(xd.L2.Message, listExtDeps, depIdx)
depIdx++ depIdx++
} }
@@ -92,7 +92,7 @@ func (file *File) resolveServices() {
} }
} }
func (file *File) resolveEnumDependency(ed pref.EnumDescriptor, i, j int32) pref.EnumDescriptor { func (file *File) resolveEnumDependency(ed protoreflect.EnumDescriptor, i, j int32) protoreflect.EnumDescriptor {
r := file.builder.FileRegistry r := file.builder.FileRegistry
if r, ok := r.(resolverByIndex); ok { if r, ok := r.(resolverByIndex); ok {
if ed2 := r.FindEnumByIndex(i, j, file.allEnums, file.allMessages); ed2 != nil { if ed2 := r.FindEnumByIndex(i, j, file.allEnums, file.allMessages); ed2 != nil {
@@ -105,12 +105,12 @@ func (file *File) resolveEnumDependency(ed pref.EnumDescriptor, i, j int32) pref
} }
} }
if d, _ := r.FindDescriptorByName(ed.FullName()); d != nil { if d, _ := r.FindDescriptorByName(ed.FullName()); d != nil {
return d.(pref.EnumDescriptor) return d.(protoreflect.EnumDescriptor)
} }
return ed return ed
} }
func (file *File) resolveMessageDependency(md pref.MessageDescriptor, i, j int32) pref.MessageDescriptor { func (file *File) resolveMessageDependency(md protoreflect.MessageDescriptor, i, j int32) protoreflect.MessageDescriptor {
r := file.builder.FileRegistry r := file.builder.FileRegistry
if r, ok := r.(resolverByIndex); ok { if r, ok := r.(resolverByIndex); ok {
if md2 := r.FindMessageByIndex(i, j, file.allEnums, file.allMessages); md2 != nil { if md2 := r.FindMessageByIndex(i, j, file.allEnums, file.allMessages); md2 != nil {
@@ -123,7 +123,7 @@ func (file *File) resolveMessageDependency(md pref.MessageDescriptor, i, j int32
} }
} }
if d, _ := r.FindDescriptorByName(md.FullName()); d != nil { if d, _ := r.FindDescriptorByName(md.FullName()); d != nil {
return d.(pref.MessageDescriptor) return d.(protoreflect.MessageDescriptor)
} }
return md return md
} }
@@ -158,7 +158,7 @@ func (fd *File) unmarshalFull(b []byte) {
if imp == nil { if imp == nil {
imp = PlaceholderFile(path) imp = PlaceholderFile(path)
} }
fd.L2.Imports = append(fd.L2.Imports, pref.FileImport{FileDescriptor: imp}) fd.L2.Imports = append(fd.L2.Imports, protoreflect.FileImport{FileDescriptor: imp})
case genid.FileDescriptorProto_EnumType_field_number: case genid.FileDescriptorProto_EnumType_field_number:
fd.L1.Enums.List[enumIdx].unmarshalFull(v, sb) fd.L1.Enums.List[enumIdx].unmarshalFull(v, sb)
enumIdx++ enumIdx++
@@ -199,7 +199,7 @@ func (ed *Enum) unmarshalFull(b []byte, sb *strs.Builder) {
case genid.EnumDescriptorProto_Value_field_number: case genid.EnumDescriptorProto_Value_field_number:
rawValues = append(rawValues, v) rawValues = append(rawValues, v)
case genid.EnumDescriptorProto_ReservedName_field_number: case genid.EnumDescriptorProto_ReservedName_field_number:
ed.L2.ReservedNames.List = append(ed.L2.ReservedNames.List, pref.Name(sb.MakeString(v))) ed.L2.ReservedNames.List = append(ed.L2.ReservedNames.List, protoreflect.Name(sb.MakeString(v)))
case genid.EnumDescriptorProto_ReservedRange_field_number: case genid.EnumDescriptorProto_ReservedRange_field_number:
ed.L2.ReservedRanges.List = append(ed.L2.ReservedRanges.List, unmarshalEnumReservedRange(v)) ed.L2.ReservedRanges.List = append(ed.L2.ReservedRanges.List, unmarshalEnumReservedRange(v))
case genid.EnumDescriptorProto_Options_field_number: case genid.EnumDescriptorProto_Options_field_number:
@@ -219,7 +219,7 @@ func (ed *Enum) unmarshalFull(b []byte, sb *strs.Builder) {
ed.L2.Options = ed.L0.ParentFile.builder.optionsUnmarshaler(&descopts.Enum, rawOptions) ed.L2.Options = ed.L0.ParentFile.builder.optionsUnmarshaler(&descopts.Enum, rawOptions)
} }
func unmarshalEnumReservedRange(b []byte) (r [2]pref.EnumNumber) { func unmarshalEnumReservedRange(b []byte) (r [2]protoreflect.EnumNumber) {
for len(b) > 0 { for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b) num, typ, n := protowire.ConsumeTag(b)
b = b[n:] b = b[n:]
@@ -229,9 +229,9 @@ func unmarshalEnumReservedRange(b []byte) (r [2]pref.EnumNumber) {
b = b[m:] b = b[m:]
switch num { switch num {
case genid.EnumDescriptorProto_EnumReservedRange_Start_field_number: case genid.EnumDescriptorProto_EnumReservedRange_Start_field_number:
r[0] = pref.EnumNumber(v) r[0] = protoreflect.EnumNumber(v)
case genid.EnumDescriptorProto_EnumReservedRange_End_field_number: case genid.EnumDescriptorProto_EnumReservedRange_End_field_number:
r[1] = pref.EnumNumber(v) r[1] = protoreflect.EnumNumber(v)
} }
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
@@ -241,7 +241,7 @@ func unmarshalEnumReservedRange(b []byte) (r [2]pref.EnumNumber) {
return r return r
} }
func (vd *EnumValue) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (vd *EnumValue) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
vd.L0.ParentFile = pf vd.L0.ParentFile = pf
vd.L0.Parent = pd vd.L0.Parent = pd
vd.L0.Index = i vd.L0.Index = i
@@ -256,7 +256,7 @@ func (vd *EnumValue) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref
b = b[m:] b = b[m:]
switch num { switch num {
case genid.EnumValueDescriptorProto_Number_field_number: case genid.EnumValueDescriptorProto_Number_field_number:
vd.L1.Number = pref.EnumNumber(v) vd.L1.Number = protoreflect.EnumNumber(v)
} }
case protowire.BytesType: case protowire.BytesType:
v, m := protowire.ConsumeBytes(b) v, m := protowire.ConsumeBytes(b)
@@ -294,7 +294,7 @@ func (md *Message) unmarshalFull(b []byte, sb *strs.Builder) {
case genid.DescriptorProto_OneofDecl_field_number: case genid.DescriptorProto_OneofDecl_field_number:
rawOneofs = append(rawOneofs, v) rawOneofs = append(rawOneofs, v)
case genid.DescriptorProto_ReservedName_field_number: case genid.DescriptorProto_ReservedName_field_number:
md.L2.ReservedNames.List = append(md.L2.ReservedNames.List, pref.Name(sb.MakeString(v))) md.L2.ReservedNames.List = append(md.L2.ReservedNames.List, protoreflect.Name(sb.MakeString(v)))
case genid.DescriptorProto_ReservedRange_field_number: case genid.DescriptorProto_ReservedRange_field_number:
md.L2.ReservedRanges.List = append(md.L2.ReservedRanges.List, unmarshalMessageReservedRange(v)) md.L2.ReservedRanges.List = append(md.L2.ReservedRanges.List, unmarshalMessageReservedRange(v))
case genid.DescriptorProto_ExtensionRange_field_number: case genid.DescriptorProto_ExtensionRange_field_number:
@@ -326,7 +326,7 @@ func (md *Message) unmarshalFull(b []byte, sb *strs.Builder) {
for i, b := range rawFields { for i, b := range rawFields {
fd := &md.L2.Fields.List[i] fd := &md.L2.Fields.List[i]
fd.unmarshalFull(b, sb, md.L0.ParentFile, md, i) fd.unmarshalFull(b, sb, md.L0.ParentFile, md, i)
if fd.L1.Cardinality == pref.Required { if fd.L1.Cardinality == protoreflect.Required {
md.L2.RequiredNumbers.List = append(md.L2.RequiredNumbers.List, fd.L1.Number) md.L2.RequiredNumbers.List = append(md.L2.RequiredNumbers.List, fd.L1.Number)
} }
} }
@@ -359,7 +359,7 @@ func (md *Message) unmarshalOptions(b []byte) {
} }
} }
func unmarshalMessageReservedRange(b []byte) (r [2]pref.FieldNumber) { func unmarshalMessageReservedRange(b []byte) (r [2]protoreflect.FieldNumber) {
for len(b) > 0 { for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b) num, typ, n := protowire.ConsumeTag(b)
b = b[n:] b = b[n:]
@@ -369,9 +369,9 @@ func unmarshalMessageReservedRange(b []byte) (r [2]pref.FieldNumber) {
b = b[m:] b = b[m:]
switch num { switch num {
case genid.DescriptorProto_ReservedRange_Start_field_number: case genid.DescriptorProto_ReservedRange_Start_field_number:
r[0] = pref.FieldNumber(v) r[0] = protoreflect.FieldNumber(v)
case genid.DescriptorProto_ReservedRange_End_field_number: case genid.DescriptorProto_ReservedRange_End_field_number:
r[1] = pref.FieldNumber(v) r[1] = protoreflect.FieldNumber(v)
} }
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
@@ -381,7 +381,7 @@ func unmarshalMessageReservedRange(b []byte) (r [2]pref.FieldNumber) {
return r return r
} }
func unmarshalMessageExtensionRange(b []byte) (r [2]pref.FieldNumber, rawOptions []byte) { func unmarshalMessageExtensionRange(b []byte) (r [2]protoreflect.FieldNumber, rawOptions []byte) {
for len(b) > 0 { for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b) num, typ, n := protowire.ConsumeTag(b)
b = b[n:] b = b[n:]
@@ -391,9 +391,9 @@ func unmarshalMessageExtensionRange(b []byte) (r [2]pref.FieldNumber, rawOptions
b = b[m:] b = b[m:]
switch num { switch num {
case genid.DescriptorProto_ExtensionRange_Start_field_number: case genid.DescriptorProto_ExtensionRange_Start_field_number:
r[0] = pref.FieldNumber(v) r[0] = protoreflect.FieldNumber(v)
case genid.DescriptorProto_ExtensionRange_End_field_number: case genid.DescriptorProto_ExtensionRange_End_field_number:
r[1] = pref.FieldNumber(v) r[1] = protoreflect.FieldNumber(v)
} }
case protowire.BytesType: case protowire.BytesType:
v, m := protowire.ConsumeBytes(b) v, m := protowire.ConsumeBytes(b)
@@ -410,10 +410,11 @@ func unmarshalMessageExtensionRange(b []byte) (r [2]pref.FieldNumber, rawOptions
return r, rawOptions return r, rawOptions
} }
func (fd *Field) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (fd *Field) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
fd.L0.ParentFile = pf fd.L0.ParentFile = pf
fd.L0.Parent = pd fd.L0.Parent = pd
fd.L0.Index = i fd.L0.Index = i
fd.L1.EditionFeatures = featuresFromParentDesc(fd.Parent())
var rawTypeName []byte var rawTypeName []byte
var rawOptions []byte var rawOptions []byte
@@ -426,11 +427,11 @@ func (fd *Field) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Des
b = b[m:] b = b[m:]
switch num { switch num {
case genid.FieldDescriptorProto_Number_field_number: case genid.FieldDescriptorProto_Number_field_number:
fd.L1.Number = pref.FieldNumber(v) fd.L1.Number = protoreflect.FieldNumber(v)
case genid.FieldDescriptorProto_Label_field_number: case genid.FieldDescriptorProto_Label_field_number:
fd.L1.Cardinality = pref.Cardinality(v) fd.L1.Cardinality = protoreflect.Cardinality(v)
case genid.FieldDescriptorProto_Type_field_number: case genid.FieldDescriptorProto_Type_field_number:
fd.L1.Kind = pref.Kind(v) fd.L1.Kind = protoreflect.Kind(v)
case genid.FieldDescriptorProto_OneofIndex_field_number: case genid.FieldDescriptorProto_OneofIndex_field_number:
// In Message.unmarshalFull, we allocate slices for both // In Message.unmarshalFull, we allocate slices for both
// the field and oneof descriptors before unmarshaling either // the field and oneof descriptors before unmarshaling either
@@ -453,7 +454,7 @@ func (fd *Field) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Des
case genid.FieldDescriptorProto_JsonName_field_number: case genid.FieldDescriptorProto_JsonName_field_number:
fd.L1.StringName.InitJSON(sb.MakeString(v)) fd.L1.StringName.InitJSON(sb.MakeString(v))
case genid.FieldDescriptorProto_DefaultValue_field_number: case genid.FieldDescriptorProto_DefaultValue_field_number:
fd.L1.Default.val = pref.ValueOfBytes(v) // temporarily store as bytes; later resolved in resolveMessages fd.L1.Default.val = protoreflect.ValueOfBytes(v) // temporarily store as bytes; later resolved in resolveMessages
case genid.FieldDescriptorProto_TypeName_field_number: case genid.FieldDescriptorProto_TypeName_field_number:
rawTypeName = v rawTypeName = v
case genid.FieldDescriptorProto_Options_field_number: case genid.FieldDescriptorProto_Options_field_number:
@@ -465,12 +466,18 @@ func (fd *Field) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Des
b = b[m:] b = b[m:]
} }
} }
if fd.Syntax() == protoreflect.Editions && fd.L1.Kind == protoreflect.MessageKind && fd.L1.EditionFeatures.IsDelimitedEncoded {
fd.L1.Kind = protoreflect.GroupKind
}
if fd.Syntax() == protoreflect.Editions && fd.L1.EditionFeatures.IsLegacyRequired {
fd.L1.Cardinality = protoreflect.Required
}
if rawTypeName != nil { if rawTypeName != nil {
name := makeFullName(sb, rawTypeName) name := makeFullName(sb, rawTypeName)
switch fd.L1.Kind { switch fd.L1.Kind {
case pref.EnumKind: case protoreflect.EnumKind:
fd.L1.Enum = PlaceholderEnum(name) fd.L1.Enum = PlaceholderEnum(name)
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
fd.L1.Message = PlaceholderMessage(name) fd.L1.Message = PlaceholderMessage(name)
} }
} }
@@ -497,6 +504,13 @@ func (fd *Field) unmarshalOptions(b []byte) {
fd.L1.HasEnforceUTF8 = true fd.L1.HasEnforceUTF8 = true
fd.L1.EnforceUTF8 = protowire.DecodeBool(v) fd.L1.EnforceUTF8 = protowire.DecodeBool(v)
} }
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.FieldOptions_Features_field_number:
fd.L1.EditionFeatures = unmarshalFeatureSet(v, fd.L1.EditionFeatures)
}
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
b = b[m:] b = b[m:]
@@ -504,7 +518,7 @@ func (fd *Field) unmarshalOptions(b []byte) {
} }
} }
func (od *Oneof) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (od *Oneof) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
od.L0.ParentFile = pf od.L0.ParentFile = pf
od.L0.Parent = pd od.L0.Parent = pd
od.L0.Index = i od.L0.Index = i
@@ -534,6 +548,7 @@ func (od *Oneof) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Des
func (xd *Extension) unmarshalFull(b []byte, sb *strs.Builder) { func (xd *Extension) unmarshalFull(b []byte, sb *strs.Builder) {
var rawTypeName []byte var rawTypeName []byte
var rawOptions []byte var rawOptions []byte
xd.L1.EditionFeatures = featuresFromParentDesc(xd.L1.Extendee)
xd.L2 = new(ExtensionL2) xd.L2 = new(ExtensionL2)
for len(b) > 0 { for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b) num, typ, n := protowire.ConsumeTag(b)
@@ -553,7 +568,7 @@ func (xd *Extension) unmarshalFull(b []byte, sb *strs.Builder) {
case genid.FieldDescriptorProto_JsonName_field_number: case genid.FieldDescriptorProto_JsonName_field_number:
xd.L2.StringName.InitJSON(sb.MakeString(v)) xd.L2.StringName.InitJSON(sb.MakeString(v))
case genid.FieldDescriptorProto_DefaultValue_field_number: case genid.FieldDescriptorProto_DefaultValue_field_number:
xd.L2.Default.val = pref.ValueOfBytes(v) // temporarily store as bytes; later resolved in resolveExtensions xd.L2.Default.val = protoreflect.ValueOfBytes(v) // temporarily store as bytes; later resolved in resolveExtensions
case genid.FieldDescriptorProto_TypeName_field_number: case genid.FieldDescriptorProto_TypeName_field_number:
rawTypeName = v rawTypeName = v
case genid.FieldDescriptorProto_Options_field_number: case genid.FieldDescriptorProto_Options_field_number:
@@ -565,12 +580,18 @@ func (xd *Extension) unmarshalFull(b []byte, sb *strs.Builder) {
b = b[m:] b = b[m:]
} }
} }
if xd.Syntax() == protoreflect.Editions && xd.L1.Kind == protoreflect.MessageKind && xd.L1.EditionFeatures.IsDelimitedEncoded {
xd.L1.Kind = protoreflect.GroupKind
}
if xd.Syntax() == protoreflect.Editions && xd.L1.EditionFeatures.IsLegacyRequired {
xd.L1.Cardinality = protoreflect.Required
}
if rawTypeName != nil { if rawTypeName != nil {
name := makeFullName(sb, rawTypeName) name := makeFullName(sb, rawTypeName)
switch xd.L1.Kind { switch xd.L1.Kind {
case pref.EnumKind: case protoreflect.EnumKind:
xd.L2.Enum = PlaceholderEnum(name) xd.L2.Enum = PlaceholderEnum(name)
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
xd.L2.Message = PlaceholderMessage(name) xd.L2.Message = PlaceholderMessage(name)
} }
} }
@@ -589,6 +610,13 @@ func (xd *Extension) unmarshalOptions(b []byte) {
case genid.FieldOptions_Packed_field_number: case genid.FieldOptions_Packed_field_number:
xd.L2.IsPacked = protowire.DecodeBool(v) xd.L2.IsPacked = protowire.DecodeBool(v)
} }
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.FieldOptions_Features_field_number:
xd.L1.EditionFeatures = unmarshalFeatureSet(v, xd.L1.EditionFeatures)
}
default: default:
m := protowire.ConsumeFieldValue(num, typ, b) m := protowire.ConsumeFieldValue(num, typ, b)
b = b[m:] b = b[m:]
@@ -627,7 +655,7 @@ func (sd *Service) unmarshalFull(b []byte, sb *strs.Builder) {
sd.L2.Options = sd.L0.ParentFile.builder.optionsUnmarshaler(&descopts.Service, rawOptions) sd.L2.Options = sd.L0.ParentFile.builder.optionsUnmarshaler(&descopts.Service, rawOptions)
} }
func (md *Method) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd pref.Descriptor, i int) { func (md *Method) unmarshalFull(b []byte, sb *strs.Builder, pf *File, pd protoreflect.Descriptor, i int) {
md.L0.ParentFile = pf md.L0.ParentFile = pf
md.L0.Parent = pd md.L0.Parent = pd
md.L0.Index = i md.L0.Index = i
@@ -680,18 +708,18 @@ func appendOptions(dst, src []byte) []byte {
// //
// The type of message to unmarshal to is passed as a pointer since the // The type of message to unmarshal to is passed as a pointer since the
// vars in descopts may not yet be populated at the time this function is called. // vars in descopts may not yet be populated at the time this function is called.
func (db *Builder) optionsUnmarshaler(p *pref.ProtoMessage, b []byte) func() pref.ProtoMessage { func (db *Builder) optionsUnmarshaler(p *protoreflect.ProtoMessage, b []byte) func() protoreflect.ProtoMessage {
if b == nil { if b == nil {
return nil return nil
} }
var opts pref.ProtoMessage var opts protoreflect.ProtoMessage
var once sync.Once var once sync.Once
return func() pref.ProtoMessage { return func() protoreflect.ProtoMessage {
once.Do(func() { once.Do(func() {
if *p == nil { if *p == nil {
panic("Descriptor.Options called without importing the descriptor package") panic("Descriptor.Options called without importing the descriptor package")
} }
opts = reflect.New(reflect.TypeOf(*p).Elem()).Interface().(pref.ProtoMessage) opts = reflect.New(reflect.TypeOf(*p).Elem()).Interface().(protoreflect.ProtoMessage)
if err := (proto.UnmarshalOptions{ if err := (proto.UnmarshalOptions{
AllowPartial: true, AllowPartial: true,
Resolver: db.TypeResolver, Resolver: db.TypeResolver,

View File

@@ -17,31 +17,30 @@ import (
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
"google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/pragma"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
pref "google.golang.org/protobuf/reflect/protoreflect"
) )
type FileImports []pref.FileImport type FileImports []protoreflect.FileImport
func (p *FileImports) Len() int { return len(*p) } func (p *FileImports) Len() int { return len(*p) }
func (p *FileImports) Get(i int) pref.FileImport { return (*p)[i] } func (p *FileImports) Get(i int) protoreflect.FileImport { return (*p)[i] }
func (p *FileImports) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) } func (p *FileImports) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) }
func (p *FileImports) ProtoInternal(pragma.DoNotImplement) {} func (p *FileImports) ProtoInternal(pragma.DoNotImplement) {}
type Names struct { type Names struct {
List []pref.Name List []protoreflect.Name
once sync.Once once sync.Once
has map[pref.Name]int // protected by once has map[protoreflect.Name]int // protected by once
} }
func (p *Names) Len() int { return len(p.List) } func (p *Names) Len() int { return len(p.List) }
func (p *Names) Get(i int) pref.Name { return p.List[i] } func (p *Names) Get(i int) protoreflect.Name { return p.List[i] }
func (p *Names) Has(s pref.Name) bool { return p.lazyInit().has[s] > 0 } func (p *Names) Has(s protoreflect.Name) bool { return p.lazyInit().has[s] > 0 }
func (p *Names) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) } func (p *Names) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) }
func (p *Names) ProtoInternal(pragma.DoNotImplement) {} func (p *Names) ProtoInternal(pragma.DoNotImplement) {}
func (p *Names) lazyInit() *Names { func (p *Names) lazyInit() *Names {
p.once.Do(func() { p.once.Do(func() {
if len(p.List) > 0 { if len(p.List) > 0 {
p.has = make(map[pref.Name]int, len(p.List)) p.has = make(map[protoreflect.Name]int, len(p.List))
for _, s := range p.List { for _, s := range p.List {
p.has[s] = p.has[s] + 1 p.has[s] = p.has[s] + 1
} }
@@ -67,14 +66,14 @@ func (p *Names) CheckValid() error {
} }
type EnumRanges struct { type EnumRanges struct {
List [][2]pref.EnumNumber // start inclusive; end inclusive List [][2]protoreflect.EnumNumber // start inclusive; end inclusive
once sync.Once once sync.Once
sorted [][2]pref.EnumNumber // protected by once sorted [][2]protoreflect.EnumNumber // protected by once
} }
func (p *EnumRanges) Len() int { return len(p.List) } func (p *EnumRanges) Len() int { return len(p.List) }
func (p *EnumRanges) Get(i int) [2]pref.EnumNumber { return p.List[i] } func (p *EnumRanges) Get(i int) [2]protoreflect.EnumNumber { return p.List[i] }
func (p *EnumRanges) Has(n pref.EnumNumber) bool { func (p *EnumRanges) Has(n protoreflect.EnumNumber) bool {
for ls := p.lazyInit().sorted; len(ls) > 0; { for ls := p.lazyInit().sorted; len(ls) > 0; {
i := len(ls) / 2 i := len(ls) / 2
switch r := enumRange(ls[i]); { switch r := enumRange(ls[i]); {
@@ -129,14 +128,14 @@ func (r enumRange) String() string {
} }
type FieldRanges struct { type FieldRanges struct {
List [][2]pref.FieldNumber // start inclusive; end exclusive List [][2]protoreflect.FieldNumber // start inclusive; end exclusive
once sync.Once once sync.Once
sorted [][2]pref.FieldNumber // protected by once sorted [][2]protoreflect.FieldNumber // protected by once
} }
func (p *FieldRanges) Len() int { return len(p.List) } func (p *FieldRanges) Len() int { return len(p.List) }
func (p *FieldRanges) Get(i int) [2]pref.FieldNumber { return p.List[i] } func (p *FieldRanges) Get(i int) [2]protoreflect.FieldNumber { return p.List[i] }
func (p *FieldRanges) Has(n pref.FieldNumber) bool { func (p *FieldRanges) Has(n protoreflect.FieldNumber) bool {
for ls := p.lazyInit().sorted; len(ls) > 0; { for ls := p.lazyInit().sorted; len(ls) > 0; {
i := len(ls) / 2 i := len(ls) / 2
switch r := fieldRange(ls[i]); { switch r := fieldRange(ls[i]); {
@@ -221,17 +220,17 @@ func (r fieldRange) String() string {
} }
type FieldNumbers struct { type FieldNumbers struct {
List []pref.FieldNumber List []protoreflect.FieldNumber
once sync.Once once sync.Once
has map[pref.FieldNumber]struct{} // protected by once has map[protoreflect.FieldNumber]struct{} // protected by once
} }
func (p *FieldNumbers) Len() int { return len(p.List) } func (p *FieldNumbers) Len() int { return len(p.List) }
func (p *FieldNumbers) Get(i int) pref.FieldNumber { return p.List[i] } func (p *FieldNumbers) Get(i int) protoreflect.FieldNumber { return p.List[i] }
func (p *FieldNumbers) Has(n pref.FieldNumber) bool { func (p *FieldNumbers) Has(n protoreflect.FieldNumber) bool {
p.once.Do(func() { p.once.Do(func() {
if len(p.List) > 0 { if len(p.List) > 0 {
p.has = make(map[pref.FieldNumber]struct{}, len(p.List)) p.has = make(map[protoreflect.FieldNumber]struct{}, len(p.List))
for _, n := range p.List { for _, n := range p.List {
p.has[n] = struct{}{} p.has[n] = struct{}{}
} }
@@ -244,30 +243,38 @@ func (p *FieldNumbers) Format(s fmt.State, r rune) { descfmt.FormatList
func (p *FieldNumbers) ProtoInternal(pragma.DoNotImplement) {} func (p *FieldNumbers) ProtoInternal(pragma.DoNotImplement) {}
type OneofFields struct { type OneofFields struct {
List []pref.FieldDescriptor List []protoreflect.FieldDescriptor
once sync.Once once sync.Once
byName map[pref.Name]pref.FieldDescriptor // protected by once byName map[protoreflect.Name]protoreflect.FieldDescriptor // protected by once
byJSON map[string]pref.FieldDescriptor // protected by once byJSON map[string]protoreflect.FieldDescriptor // protected by once
byText map[string]pref.FieldDescriptor // protected by once byText map[string]protoreflect.FieldDescriptor // protected by once
byNum map[pref.FieldNumber]pref.FieldDescriptor // protected by once byNum map[protoreflect.FieldNumber]protoreflect.FieldDescriptor // protected by once
} }
func (p *OneofFields) Len() int { return len(p.List) } func (p *OneofFields) Len() int { return len(p.List) }
func (p *OneofFields) Get(i int) pref.FieldDescriptor { return p.List[i] } func (p *OneofFields) Get(i int) protoreflect.FieldDescriptor { return p.List[i] }
func (p *OneofFields) ByName(s pref.Name) pref.FieldDescriptor { return p.lazyInit().byName[s] } func (p *OneofFields) ByName(s protoreflect.Name) protoreflect.FieldDescriptor {
func (p *OneofFields) ByJSONName(s string) pref.FieldDescriptor { return p.lazyInit().byJSON[s] } return p.lazyInit().byName[s]
func (p *OneofFields) ByTextName(s string) pref.FieldDescriptor { return p.lazyInit().byText[s] } }
func (p *OneofFields) ByNumber(n pref.FieldNumber) pref.FieldDescriptor { return p.lazyInit().byNum[n] } func (p *OneofFields) ByJSONName(s string) protoreflect.FieldDescriptor {
return p.lazyInit().byJSON[s]
}
func (p *OneofFields) ByTextName(s string) protoreflect.FieldDescriptor {
return p.lazyInit().byText[s]
}
func (p *OneofFields) ByNumber(n protoreflect.FieldNumber) protoreflect.FieldDescriptor {
return p.lazyInit().byNum[n]
}
func (p *OneofFields) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) } func (p *OneofFields) Format(s fmt.State, r rune) { descfmt.FormatList(s, r, p) }
func (p *OneofFields) ProtoInternal(pragma.DoNotImplement) {} func (p *OneofFields) ProtoInternal(pragma.DoNotImplement) {}
func (p *OneofFields) lazyInit() *OneofFields { func (p *OneofFields) lazyInit() *OneofFields {
p.once.Do(func() { p.once.Do(func() {
if len(p.List) > 0 { if len(p.List) > 0 {
p.byName = make(map[pref.Name]pref.FieldDescriptor, len(p.List)) p.byName = make(map[protoreflect.Name]protoreflect.FieldDescriptor, len(p.List))
p.byJSON = make(map[string]pref.FieldDescriptor, len(p.List)) p.byJSON = make(map[string]protoreflect.FieldDescriptor, len(p.List))
p.byText = make(map[string]pref.FieldDescriptor, len(p.List)) p.byText = make(map[string]protoreflect.FieldDescriptor, len(p.List))
p.byNum = make(map[pref.FieldNumber]pref.FieldDescriptor, len(p.List)) p.byNum = make(map[protoreflect.FieldNumber]protoreflect.FieldDescriptor, len(p.List))
for _, f := range p.List { for _, f := range p.List {
// Field names and numbers are guaranteed to be unique. // Field names and numbers are guaranteed to be unique.
p.byName[f.Name()] = f p.byName[f.Name()] = f
@@ -284,123 +291,123 @@ type SourceLocations struct {
// List is a list of SourceLocations. // List is a list of SourceLocations.
// The SourceLocation.Next field does not need to be populated // The SourceLocation.Next field does not need to be populated
// as it will be lazily populated upon first need. // as it will be lazily populated upon first need.
List []pref.SourceLocation List []protoreflect.SourceLocation
// File is the parent file descriptor that these locations are relative to. // File is the parent file descriptor that these locations are relative to.
// If non-nil, ByDescriptor verifies that the provided descriptor // If non-nil, ByDescriptor verifies that the provided descriptor
// is a child of this file descriptor. // is a child of this file descriptor.
File pref.FileDescriptor File protoreflect.FileDescriptor
once sync.Once once sync.Once
byPath map[pathKey]int byPath map[pathKey]int
} }
func (p *SourceLocations) Len() int { return len(p.List) } func (p *SourceLocations) Len() int { return len(p.List) }
func (p *SourceLocations) Get(i int) pref.SourceLocation { return p.lazyInit().List[i] } func (p *SourceLocations) Get(i int) protoreflect.SourceLocation { return p.lazyInit().List[i] }
func (p *SourceLocations) byKey(k pathKey) pref.SourceLocation { func (p *SourceLocations) byKey(k pathKey) protoreflect.SourceLocation {
if i, ok := p.lazyInit().byPath[k]; ok { if i, ok := p.lazyInit().byPath[k]; ok {
return p.List[i] return p.List[i]
} }
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
func (p *SourceLocations) ByPath(path pref.SourcePath) pref.SourceLocation { func (p *SourceLocations) ByPath(path protoreflect.SourcePath) protoreflect.SourceLocation {
return p.byKey(newPathKey(path)) return p.byKey(newPathKey(path))
} }
func (p *SourceLocations) ByDescriptor(desc pref.Descriptor) pref.SourceLocation { func (p *SourceLocations) ByDescriptor(desc protoreflect.Descriptor) protoreflect.SourceLocation {
if p.File != nil && desc != nil && p.File != desc.ParentFile() { if p.File != nil && desc != nil && p.File != desc.ParentFile() {
return pref.SourceLocation{} // mismatching parent files return protoreflect.SourceLocation{} // mismatching parent files
} }
var pathArr [16]int32 var pathArr [16]int32
path := pathArr[:0] path := pathArr[:0]
for { for {
switch desc.(type) { switch desc.(type) {
case pref.FileDescriptor: case protoreflect.FileDescriptor:
// Reverse the path since it was constructed in reverse. // Reverse the path since it was constructed in reverse.
for i, j := 0, len(path)-1; i < j; i, j = i+1, j-1 { for i, j := 0, len(path)-1; i < j; i, j = i+1, j-1 {
path[i], path[j] = path[j], path[i] path[i], path[j] = path[j], path[i]
} }
return p.byKey(newPathKey(path)) return p.byKey(newPathKey(path))
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.FileDescriptor: case protoreflect.FileDescriptor:
path = append(path, int32(genid.FileDescriptorProto_MessageType_field_number)) path = append(path, int32(genid.FileDescriptorProto_MessageType_field_number))
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(genid.DescriptorProto_NestedType_field_number)) path = append(path, int32(genid.DescriptorProto_NestedType_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
case pref.FieldDescriptor: case protoreflect.FieldDescriptor:
isExtension := desc.(pref.FieldDescriptor).IsExtension() isExtension := desc.(protoreflect.FieldDescriptor).IsExtension()
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
if isExtension { if isExtension {
switch desc.(type) { switch desc.(type) {
case pref.FileDescriptor: case protoreflect.FileDescriptor:
path = append(path, int32(genid.FileDescriptorProto_Extension_field_number)) path = append(path, int32(genid.FileDescriptorProto_Extension_field_number))
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(genid.DescriptorProto_Extension_field_number)) path = append(path, int32(genid.DescriptorProto_Extension_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
} else { } else {
switch desc.(type) { switch desc.(type) {
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(genid.DescriptorProto_Field_field_number)) path = append(path, int32(genid.DescriptorProto_Field_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
} }
case pref.OneofDescriptor: case protoreflect.OneofDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(genid.DescriptorProto_OneofDecl_field_number)) path = append(path, int32(genid.DescriptorProto_OneofDecl_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
case pref.EnumDescriptor: case protoreflect.EnumDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.FileDescriptor: case protoreflect.FileDescriptor:
path = append(path, int32(genid.FileDescriptorProto_EnumType_field_number)) path = append(path, int32(genid.FileDescriptorProto_EnumType_field_number))
case pref.MessageDescriptor: case protoreflect.MessageDescriptor:
path = append(path, int32(genid.DescriptorProto_EnumType_field_number)) path = append(path, int32(genid.DescriptorProto_EnumType_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
case pref.EnumValueDescriptor: case protoreflect.EnumValueDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.EnumDescriptor: case protoreflect.EnumDescriptor:
path = append(path, int32(genid.EnumDescriptorProto_Value_field_number)) path = append(path, int32(genid.EnumDescriptorProto_Value_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
case pref.ServiceDescriptor: case protoreflect.ServiceDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.FileDescriptor: case protoreflect.FileDescriptor:
path = append(path, int32(genid.FileDescriptorProto_Service_field_number)) path = append(path, int32(genid.FileDescriptorProto_Service_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
case pref.MethodDescriptor: case protoreflect.MethodDescriptor:
path = append(path, int32(desc.Index())) path = append(path, int32(desc.Index()))
desc = desc.Parent() desc = desc.Parent()
switch desc.(type) { switch desc.(type) {
case pref.ServiceDescriptor: case protoreflect.ServiceDescriptor:
path = append(path, int32(genid.ServiceDescriptorProto_Method_field_number)) path = append(path, int32(genid.ServiceDescriptorProto_Method_field_number))
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
default: default:
return pref.SourceLocation{} return protoreflect.SourceLocation{}
} }
} }
} }
@@ -435,7 +442,7 @@ type pathKey struct {
str string // used if the path does not fit in arr str string // used if the path does not fit in arr
} }
func newPathKey(p pref.SourcePath) (k pathKey) { func newPathKey(p protoreflect.SourcePath) (k pathKey) {
if len(p) < len(k.arr) { if len(p) < len(k.arr) {
for i, ps := range p { for i, ps := range p {
if ps < 0 || math.MaxUint8 <= ps { if ps < 0 || math.MaxUint8 <= ps {

View File

@@ -0,0 +1,142 @@
// Copyright 2024 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package filedesc
import (
"fmt"
"google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/editiondefaults"
"google.golang.org/protobuf/internal/genid"
"google.golang.org/protobuf/reflect/protoreflect"
)
var defaultsCache = make(map[Edition]EditionFeatures)
func init() {
unmarshalEditionDefaults(editiondefaults.Defaults)
}
func unmarshalGoFeature(b []byte, parent EditionFeatures) EditionFeatures {
for len(b) > 0 {
num, _, n := protowire.ConsumeTag(b)
b = b[n:]
switch num {
case genid.GoFeatures_LegacyUnmarshalJsonEnum_field_number:
v, m := protowire.ConsumeVarint(b)
b = b[m:]
parent.GenerateLegacyUnmarshalJSON = protowire.DecodeBool(v)
default:
panic(fmt.Sprintf("unkown field number %d while unmarshalling GoFeatures", num))
}
}
return parent
}
func unmarshalFeatureSet(b []byte, parent EditionFeatures) EditionFeatures {
for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b)
b = b[n:]
switch typ {
case protowire.VarintType:
v, m := protowire.ConsumeVarint(b)
b = b[m:]
switch num {
case genid.FeatureSet_FieldPresence_field_number:
parent.IsFieldPresence = v == genid.FeatureSet_EXPLICIT_enum_value || v == genid.FeatureSet_LEGACY_REQUIRED_enum_value
parent.IsLegacyRequired = v == genid.FeatureSet_LEGACY_REQUIRED_enum_value
case genid.FeatureSet_EnumType_field_number:
parent.IsOpenEnum = v == genid.FeatureSet_OPEN_enum_value
case genid.FeatureSet_RepeatedFieldEncoding_field_number:
parent.IsPacked = v == genid.FeatureSet_PACKED_enum_value
case genid.FeatureSet_Utf8Validation_field_number:
parent.IsUTF8Validated = v == genid.FeatureSet_VERIFY_enum_value
case genid.FeatureSet_MessageEncoding_field_number:
parent.IsDelimitedEncoded = v == genid.FeatureSet_DELIMITED_enum_value
case genid.FeatureSet_JsonFormat_field_number:
parent.IsJSONCompliant = v == genid.FeatureSet_ALLOW_enum_value
default:
panic(fmt.Sprintf("unkown field number %d while unmarshalling FeatureSet", num))
}
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.GoFeatures_LegacyUnmarshalJsonEnum_field_number:
parent = unmarshalGoFeature(v, parent)
}
}
}
return parent
}
func featuresFromParentDesc(parentDesc protoreflect.Descriptor) EditionFeatures {
var parentFS EditionFeatures
switch p := parentDesc.(type) {
case *File:
parentFS = p.L1.EditionFeatures
case *Message:
parentFS = p.L1.EditionFeatures
default:
panic(fmt.Sprintf("unknown parent type %T", parentDesc))
}
return parentFS
}
func unmarshalEditionDefault(b []byte) {
var ed Edition
var fs EditionFeatures
for len(b) > 0 {
num, typ, n := protowire.ConsumeTag(b)
b = b[n:]
switch typ {
case protowire.VarintType:
v, m := protowire.ConsumeVarint(b)
b = b[m:]
switch num {
case genid.FeatureSetDefaults_FeatureSetEditionDefault_Edition_field_number:
ed = Edition(v)
}
case protowire.BytesType:
v, m := protowire.ConsumeBytes(b)
b = b[m:]
switch num {
case genid.FeatureSetDefaults_FeatureSetEditionDefault_Features_field_number:
fs = unmarshalFeatureSet(v, fs)
}
}
}
defaultsCache[ed] = fs
}
func unmarshalEditionDefaults(b []byte) {
for len(b) > 0 {
num, _, n := protowire.ConsumeTag(b)
b = b[n:]
switch num {
case genid.FeatureSetDefaults_Defaults_field_number:
def, m := protowire.ConsumeBytes(b)
b = b[m:]
unmarshalEditionDefault(def)
case genid.FeatureSetDefaults_MinimumEdition_field_number,
genid.FeatureSetDefaults_MaximumEdition_field_number:
// We don't care about the minimum and maximum editions. If the
// edition we are looking for later on is not in the cache we know
// it is outside of the range between minimum and maximum edition.
_, m := protowire.ConsumeVarint(b)
b = b[m:]
default:
panic(fmt.Sprintf("unkown field number %d while unmarshalling EditionDefault", num))
}
}
}
func getFeaturesFor(ed Edition) EditionFeatures {
if def, ok := defaultsCache[ed]; ok {
return def
}
panic(fmt.Sprintf("unsupported edition: %v", ed))
}

View File

@@ -7,7 +7,7 @@ package filedesc
import ( import (
"google.golang.org/protobuf/internal/descopts" "google.golang.org/protobuf/internal/descopts"
"google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/pragma"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
var ( var (
@@ -30,78 +30,80 @@ var (
// PlaceholderFile is a placeholder, representing only the file path. // PlaceholderFile is a placeholder, representing only the file path.
type PlaceholderFile string type PlaceholderFile string
func (f PlaceholderFile) ParentFile() pref.FileDescriptor { return f } func (f PlaceholderFile) ParentFile() protoreflect.FileDescriptor { return f }
func (f PlaceholderFile) Parent() pref.Descriptor { return nil } func (f PlaceholderFile) Parent() protoreflect.Descriptor { return nil }
func (f PlaceholderFile) Index() int { return 0 } func (f PlaceholderFile) Index() int { return 0 }
func (f PlaceholderFile) Syntax() pref.Syntax { return 0 } func (f PlaceholderFile) Syntax() protoreflect.Syntax { return 0 }
func (f PlaceholderFile) Name() pref.Name { return "" } func (f PlaceholderFile) Name() protoreflect.Name { return "" }
func (f PlaceholderFile) FullName() pref.FullName { return "" } func (f PlaceholderFile) FullName() protoreflect.FullName { return "" }
func (f PlaceholderFile) IsPlaceholder() bool { return true } func (f PlaceholderFile) IsPlaceholder() bool { return true }
func (f PlaceholderFile) Options() pref.ProtoMessage { return descopts.File } func (f PlaceholderFile) Options() protoreflect.ProtoMessage { return descopts.File }
func (f PlaceholderFile) Path() string { return string(f) } func (f PlaceholderFile) Path() string { return string(f) }
func (f PlaceholderFile) Package() pref.FullName { return "" } func (f PlaceholderFile) Package() protoreflect.FullName { return "" }
func (f PlaceholderFile) Imports() pref.FileImports { return emptyFiles } func (f PlaceholderFile) Imports() protoreflect.FileImports { return emptyFiles }
func (f PlaceholderFile) Messages() pref.MessageDescriptors { return emptyMessages } func (f PlaceholderFile) Messages() protoreflect.MessageDescriptors { return emptyMessages }
func (f PlaceholderFile) Enums() pref.EnumDescriptors { return emptyEnums } func (f PlaceholderFile) Enums() protoreflect.EnumDescriptors { return emptyEnums }
func (f PlaceholderFile) Extensions() pref.ExtensionDescriptors { return emptyExtensions } func (f PlaceholderFile) Extensions() protoreflect.ExtensionDescriptors { return emptyExtensions }
func (f PlaceholderFile) Services() pref.ServiceDescriptors { return emptyServices } func (f PlaceholderFile) Services() protoreflect.ServiceDescriptors { return emptyServices }
func (f PlaceholderFile) SourceLocations() pref.SourceLocations { return emptySourceLocations } func (f PlaceholderFile) SourceLocations() protoreflect.SourceLocations { return emptySourceLocations }
func (f PlaceholderFile) ProtoType(pref.FileDescriptor) { return } func (f PlaceholderFile) ProtoType(protoreflect.FileDescriptor) { return }
func (f PlaceholderFile) ProtoInternal(pragma.DoNotImplement) { return } func (f PlaceholderFile) ProtoInternal(pragma.DoNotImplement) { return }
// PlaceholderEnum is a placeholder, representing only the full name. // PlaceholderEnum is a placeholder, representing only the full name.
type PlaceholderEnum pref.FullName type PlaceholderEnum protoreflect.FullName
func (e PlaceholderEnum) ParentFile() pref.FileDescriptor { return nil } func (e PlaceholderEnum) ParentFile() protoreflect.FileDescriptor { return nil }
func (e PlaceholderEnum) Parent() pref.Descriptor { return nil } func (e PlaceholderEnum) Parent() protoreflect.Descriptor { return nil }
func (e PlaceholderEnum) Index() int { return 0 } func (e PlaceholderEnum) Index() int { return 0 }
func (e PlaceholderEnum) Syntax() pref.Syntax { return 0 } func (e PlaceholderEnum) Syntax() protoreflect.Syntax { return 0 }
func (e PlaceholderEnum) Name() pref.Name { return pref.FullName(e).Name() } func (e PlaceholderEnum) Name() protoreflect.Name { return protoreflect.FullName(e).Name() }
func (e PlaceholderEnum) FullName() pref.FullName { return pref.FullName(e) } func (e PlaceholderEnum) FullName() protoreflect.FullName { return protoreflect.FullName(e) }
func (e PlaceholderEnum) IsPlaceholder() bool { return true } func (e PlaceholderEnum) IsPlaceholder() bool { return true }
func (e PlaceholderEnum) Options() pref.ProtoMessage { return descopts.Enum } func (e PlaceholderEnum) Options() protoreflect.ProtoMessage { return descopts.Enum }
func (e PlaceholderEnum) Values() pref.EnumValueDescriptors { return emptyEnumValues } func (e PlaceholderEnum) Values() protoreflect.EnumValueDescriptors { return emptyEnumValues }
func (e PlaceholderEnum) ReservedNames() pref.Names { return emptyNames } func (e PlaceholderEnum) ReservedNames() protoreflect.Names { return emptyNames }
func (e PlaceholderEnum) ReservedRanges() pref.EnumRanges { return emptyEnumRanges } func (e PlaceholderEnum) ReservedRanges() protoreflect.EnumRanges { return emptyEnumRanges }
func (e PlaceholderEnum) ProtoType(pref.EnumDescriptor) { return } func (e PlaceholderEnum) ProtoType(protoreflect.EnumDescriptor) { return }
func (e PlaceholderEnum) ProtoInternal(pragma.DoNotImplement) { return } func (e PlaceholderEnum) ProtoInternal(pragma.DoNotImplement) { return }
// PlaceholderEnumValue is a placeholder, representing only the full name. // PlaceholderEnumValue is a placeholder, representing only the full name.
type PlaceholderEnumValue pref.FullName type PlaceholderEnumValue protoreflect.FullName
func (e PlaceholderEnumValue) ParentFile() pref.FileDescriptor { return nil } func (e PlaceholderEnumValue) ParentFile() protoreflect.FileDescriptor { return nil }
func (e PlaceholderEnumValue) Parent() pref.Descriptor { return nil } func (e PlaceholderEnumValue) Parent() protoreflect.Descriptor { return nil }
func (e PlaceholderEnumValue) Index() int { return 0 } func (e PlaceholderEnumValue) Index() int { return 0 }
func (e PlaceholderEnumValue) Syntax() pref.Syntax { return 0 } func (e PlaceholderEnumValue) Syntax() protoreflect.Syntax { return 0 }
func (e PlaceholderEnumValue) Name() pref.Name { return pref.FullName(e).Name() } func (e PlaceholderEnumValue) Name() protoreflect.Name { return protoreflect.FullName(e).Name() }
func (e PlaceholderEnumValue) FullName() pref.FullName { return pref.FullName(e) } func (e PlaceholderEnumValue) FullName() protoreflect.FullName { return protoreflect.FullName(e) }
func (e PlaceholderEnumValue) IsPlaceholder() bool { return true } func (e PlaceholderEnumValue) IsPlaceholder() bool { return true }
func (e PlaceholderEnumValue) Options() pref.ProtoMessage { return descopts.EnumValue } func (e PlaceholderEnumValue) Options() protoreflect.ProtoMessage { return descopts.EnumValue }
func (e PlaceholderEnumValue) Number() pref.EnumNumber { return 0 } func (e PlaceholderEnumValue) Number() protoreflect.EnumNumber { return 0 }
func (e PlaceholderEnumValue) ProtoType(pref.EnumValueDescriptor) { return } func (e PlaceholderEnumValue) ProtoType(protoreflect.EnumValueDescriptor) { return }
func (e PlaceholderEnumValue) ProtoInternal(pragma.DoNotImplement) { return } func (e PlaceholderEnumValue) ProtoInternal(pragma.DoNotImplement) { return }
// PlaceholderMessage is a placeholder, representing only the full name. // PlaceholderMessage is a placeholder, representing only the full name.
type PlaceholderMessage pref.FullName type PlaceholderMessage protoreflect.FullName
func (m PlaceholderMessage) ParentFile() pref.FileDescriptor { return nil } func (m PlaceholderMessage) ParentFile() protoreflect.FileDescriptor { return nil }
func (m PlaceholderMessage) Parent() pref.Descriptor { return nil } func (m PlaceholderMessage) Parent() protoreflect.Descriptor { return nil }
func (m PlaceholderMessage) Index() int { return 0 } func (m PlaceholderMessage) Index() int { return 0 }
func (m PlaceholderMessage) Syntax() pref.Syntax { return 0 } func (m PlaceholderMessage) Syntax() protoreflect.Syntax { return 0 }
func (m PlaceholderMessage) Name() pref.Name { return pref.FullName(m).Name() } func (m PlaceholderMessage) Name() protoreflect.Name { return protoreflect.FullName(m).Name() }
func (m PlaceholderMessage) FullName() pref.FullName { return pref.FullName(m) } func (m PlaceholderMessage) FullName() protoreflect.FullName { return protoreflect.FullName(m) }
func (m PlaceholderMessage) IsPlaceholder() bool { return true } func (m PlaceholderMessage) IsPlaceholder() bool { return true }
func (m PlaceholderMessage) Options() pref.ProtoMessage { return descopts.Message } func (m PlaceholderMessage) Options() protoreflect.ProtoMessage { return descopts.Message }
func (m PlaceholderMessage) IsMapEntry() bool { return false } func (m PlaceholderMessage) IsMapEntry() bool { return false }
func (m PlaceholderMessage) Fields() pref.FieldDescriptors { return emptyFields } func (m PlaceholderMessage) Fields() protoreflect.FieldDescriptors { return emptyFields }
func (m PlaceholderMessage) Oneofs() pref.OneofDescriptors { return emptyOneofs } func (m PlaceholderMessage) Oneofs() protoreflect.OneofDescriptors { return emptyOneofs }
func (m PlaceholderMessage) ReservedNames() pref.Names { return emptyNames } func (m PlaceholderMessage) ReservedNames() protoreflect.Names { return emptyNames }
func (m PlaceholderMessage) ReservedRanges() pref.FieldRanges { return emptyFieldRanges } func (m PlaceholderMessage) ReservedRanges() protoreflect.FieldRanges { return emptyFieldRanges }
func (m PlaceholderMessage) RequiredNumbers() pref.FieldNumbers { return emptyFieldNumbers } func (m PlaceholderMessage) RequiredNumbers() protoreflect.FieldNumbers { return emptyFieldNumbers }
func (m PlaceholderMessage) ExtensionRanges() pref.FieldRanges { return emptyFieldRanges } func (m PlaceholderMessage) ExtensionRanges() protoreflect.FieldRanges { return emptyFieldRanges }
func (m PlaceholderMessage) ExtensionRangeOptions(int) pref.ProtoMessage { panic("index out of range") } func (m PlaceholderMessage) ExtensionRangeOptions(int) protoreflect.ProtoMessage {
func (m PlaceholderMessage) Messages() pref.MessageDescriptors { return emptyMessages } panic("index out of range")
func (m PlaceholderMessage) Enums() pref.EnumDescriptors { return emptyEnums } }
func (m PlaceholderMessage) Extensions() pref.ExtensionDescriptors { return emptyExtensions } func (m PlaceholderMessage) Messages() protoreflect.MessageDescriptors { return emptyMessages }
func (m PlaceholderMessage) ProtoType(pref.MessageDescriptor) { return } func (m PlaceholderMessage) Enums() protoreflect.EnumDescriptors { return emptyEnums }
func (m PlaceholderMessage) Extensions() protoreflect.ExtensionDescriptors { return emptyExtensions }
func (m PlaceholderMessage) ProtoType(protoreflect.MessageDescriptor) { return }
func (m PlaceholderMessage) ProtoInternal(pragma.DoNotImplement) { return } func (m PlaceholderMessage) ProtoInternal(pragma.DoNotImplement) { return }

View File

@@ -10,17 +10,16 @@ import (
"reflect" "reflect"
"google.golang.org/protobuf/internal/descopts" "google.golang.org/protobuf/internal/descopts"
fdesc "google.golang.org/protobuf/internal/filedesc" "google.golang.org/protobuf/internal/filedesc"
pimpl "google.golang.org/protobuf/internal/impl" pimpl "google.golang.org/protobuf/internal/impl"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
preg "google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
) )
// Builder constructs type descriptors from a raw file descriptor // Builder constructs type descriptors from a raw file descriptor
// and associated Go types for each enum and message declaration. // and associated Go types for each enum and message declaration.
// //
// // # Flattened Ordering
// Flattened Ordering
// //
// The protobuf type system represents declarations as a tree. Certain nodes in // The protobuf type system represents declarations as a tree. Certain nodes in
// the tree require us to either associate it with a concrete Go type or to // the tree require us to either associate it with a concrete Go type or to
@@ -52,7 +51,7 @@ import (
// that children themselves may have. // that children themselves may have.
type Builder struct { type Builder struct {
// File is the underlying file descriptor builder. // File is the underlying file descriptor builder.
File fdesc.Builder File filedesc.Builder
// GoTypes is a unique set of the Go types for all declarations and // GoTypes is a unique set of the Go types for all declarations and
// dependencies. Each type is represented as a zero value of the Go type. // dependencies. Each type is represented as a zero value of the Go type.
@@ -108,22 +107,22 @@ type Builder struct {
// TypeRegistry is the registry to register each type descriptor. // TypeRegistry is the registry to register each type descriptor.
// If nil, it uses protoregistry.GlobalTypes. // If nil, it uses protoregistry.GlobalTypes.
TypeRegistry interface { TypeRegistry interface {
RegisterMessage(pref.MessageType) error RegisterMessage(protoreflect.MessageType) error
RegisterEnum(pref.EnumType) error RegisterEnum(protoreflect.EnumType) error
RegisterExtension(pref.ExtensionType) error RegisterExtension(protoreflect.ExtensionType) error
} }
} }
// Out is the output of the builder. // Out is the output of the builder.
type Out struct { type Out struct {
File pref.FileDescriptor File protoreflect.FileDescriptor
} }
func (tb Builder) Build() (out Out) { func (tb Builder) Build() (out Out) {
// Replace the resolver with one that resolves dependencies by index, // Replace the resolver with one that resolves dependencies by index,
// which is faster and more reliable than relying on the global registry. // which is faster and more reliable than relying on the global registry.
if tb.File.FileRegistry == nil { if tb.File.FileRegistry == nil {
tb.File.FileRegistry = preg.GlobalFiles tb.File.FileRegistry = protoregistry.GlobalFiles
} }
tb.File.FileRegistry = &resolverByIndex{ tb.File.FileRegistry = &resolverByIndex{
goTypes: tb.GoTypes, goTypes: tb.GoTypes,
@@ -133,7 +132,7 @@ func (tb Builder) Build() (out Out) {
// Initialize registry if unpopulated. // Initialize registry if unpopulated.
if tb.TypeRegistry == nil { if tb.TypeRegistry == nil {
tb.TypeRegistry = preg.GlobalTypes tb.TypeRegistry = protoregistry.GlobalTypes
} }
fbOut := tb.File.Build() fbOut := tb.File.Build()
@@ -183,23 +182,23 @@ func (tb Builder) Build() (out Out) {
for i := range fbOut.Messages { for i := range fbOut.Messages {
switch fbOut.Messages[i].Name() { switch fbOut.Messages[i].Name() {
case "FileOptions": case "FileOptions":
descopts.File = messageGoTypes[i].(pref.ProtoMessage) descopts.File = messageGoTypes[i].(protoreflect.ProtoMessage)
case "EnumOptions": case "EnumOptions":
descopts.Enum = messageGoTypes[i].(pref.ProtoMessage) descopts.Enum = messageGoTypes[i].(protoreflect.ProtoMessage)
case "EnumValueOptions": case "EnumValueOptions":
descopts.EnumValue = messageGoTypes[i].(pref.ProtoMessage) descopts.EnumValue = messageGoTypes[i].(protoreflect.ProtoMessage)
case "MessageOptions": case "MessageOptions":
descopts.Message = messageGoTypes[i].(pref.ProtoMessage) descopts.Message = messageGoTypes[i].(protoreflect.ProtoMessage)
case "FieldOptions": case "FieldOptions":
descopts.Field = messageGoTypes[i].(pref.ProtoMessage) descopts.Field = messageGoTypes[i].(protoreflect.ProtoMessage)
case "OneofOptions": case "OneofOptions":
descopts.Oneof = messageGoTypes[i].(pref.ProtoMessage) descopts.Oneof = messageGoTypes[i].(protoreflect.ProtoMessage)
case "ExtensionRangeOptions": case "ExtensionRangeOptions":
descopts.ExtensionRange = messageGoTypes[i].(pref.ProtoMessage) descopts.ExtensionRange = messageGoTypes[i].(protoreflect.ProtoMessage)
case "ServiceOptions": case "ServiceOptions":
descopts.Service = messageGoTypes[i].(pref.ProtoMessage) descopts.Service = messageGoTypes[i].(protoreflect.ProtoMessage)
case "MethodOptions": case "MethodOptions":
descopts.Method = messageGoTypes[i].(pref.ProtoMessage) descopts.Method = messageGoTypes[i].(protoreflect.ProtoMessage)
} }
} }
} }
@@ -216,11 +215,11 @@ func (tb Builder) Build() (out Out) {
const listExtDeps = 2 const listExtDeps = 2
var goType reflect.Type var goType reflect.Type
switch fbOut.Extensions[i].L1.Kind { switch fbOut.Extensions[i].L1.Kind {
case pref.EnumKind: case protoreflect.EnumKind:
j := depIdxs.Get(tb.DependencyIndexes, listExtDeps, depIdx) j := depIdxs.Get(tb.DependencyIndexes, listExtDeps, depIdx)
goType = reflect.TypeOf(tb.GoTypes[j]) goType = reflect.TypeOf(tb.GoTypes[j])
depIdx++ depIdx++
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
j := depIdxs.Get(tb.DependencyIndexes, listExtDeps, depIdx) j := depIdxs.Get(tb.DependencyIndexes, listExtDeps, depIdx)
goType = reflect.TypeOf(tb.GoTypes[j]) goType = reflect.TypeOf(tb.GoTypes[j])
depIdx++ depIdx++
@@ -242,22 +241,22 @@ func (tb Builder) Build() (out Out) {
return out return out
} }
var goTypeForPBKind = map[pref.Kind]reflect.Type{ var goTypeForPBKind = map[protoreflect.Kind]reflect.Type{
pref.BoolKind: reflect.TypeOf(bool(false)), protoreflect.BoolKind: reflect.TypeOf(bool(false)),
pref.Int32Kind: reflect.TypeOf(int32(0)), protoreflect.Int32Kind: reflect.TypeOf(int32(0)),
pref.Sint32Kind: reflect.TypeOf(int32(0)), protoreflect.Sint32Kind: reflect.TypeOf(int32(0)),
pref.Sfixed32Kind: reflect.TypeOf(int32(0)), protoreflect.Sfixed32Kind: reflect.TypeOf(int32(0)),
pref.Int64Kind: reflect.TypeOf(int64(0)), protoreflect.Int64Kind: reflect.TypeOf(int64(0)),
pref.Sint64Kind: reflect.TypeOf(int64(0)), protoreflect.Sint64Kind: reflect.TypeOf(int64(0)),
pref.Sfixed64Kind: reflect.TypeOf(int64(0)), protoreflect.Sfixed64Kind: reflect.TypeOf(int64(0)),
pref.Uint32Kind: reflect.TypeOf(uint32(0)), protoreflect.Uint32Kind: reflect.TypeOf(uint32(0)),
pref.Fixed32Kind: reflect.TypeOf(uint32(0)), protoreflect.Fixed32Kind: reflect.TypeOf(uint32(0)),
pref.Uint64Kind: reflect.TypeOf(uint64(0)), protoreflect.Uint64Kind: reflect.TypeOf(uint64(0)),
pref.Fixed64Kind: reflect.TypeOf(uint64(0)), protoreflect.Fixed64Kind: reflect.TypeOf(uint64(0)),
pref.FloatKind: reflect.TypeOf(float32(0)), protoreflect.FloatKind: reflect.TypeOf(float32(0)),
pref.DoubleKind: reflect.TypeOf(float64(0)), protoreflect.DoubleKind: reflect.TypeOf(float64(0)),
pref.StringKind: reflect.TypeOf(string("")), protoreflect.StringKind: reflect.TypeOf(string("")),
pref.BytesKind: reflect.TypeOf([]byte(nil)), protoreflect.BytesKind: reflect.TypeOf([]byte(nil)),
} }
type depIdxs []int32 type depIdxs []int32
@@ -274,13 +273,13 @@ type (
fileRegistry fileRegistry
} }
fileRegistry interface { fileRegistry interface {
FindFileByPath(string) (pref.FileDescriptor, error) FindFileByPath(string) (protoreflect.FileDescriptor, error)
FindDescriptorByName(pref.FullName) (pref.Descriptor, error) FindDescriptorByName(protoreflect.FullName) (protoreflect.Descriptor, error)
RegisterFile(pref.FileDescriptor) error RegisterFile(protoreflect.FileDescriptor) error
} }
) )
func (r *resolverByIndex) FindEnumByIndex(i, j int32, es []fdesc.Enum, ms []fdesc.Message) pref.EnumDescriptor { func (r *resolverByIndex) FindEnumByIndex(i, j int32, es []filedesc.Enum, ms []filedesc.Message) protoreflect.EnumDescriptor {
if depIdx := int(r.depIdxs.Get(i, j)); int(depIdx) < len(es)+len(ms) { if depIdx := int(r.depIdxs.Get(i, j)); int(depIdx) < len(es)+len(ms) {
return &es[depIdx] return &es[depIdx]
} else { } else {
@@ -288,7 +287,7 @@ func (r *resolverByIndex) FindEnumByIndex(i, j int32, es []fdesc.Enum, ms []fdes
} }
} }
func (r *resolverByIndex) FindMessageByIndex(i, j int32, es []fdesc.Enum, ms []fdesc.Message) pref.MessageDescriptor { func (r *resolverByIndex) FindMessageByIndex(i, j int32, es []filedesc.Enum, ms []filedesc.Message) protoreflect.MessageDescriptor {
if depIdx := int(r.depIdxs.Get(i, j)); depIdx < len(es)+len(ms) { if depIdx := int(r.depIdxs.Get(i, j)); depIdx < len(es)+len(ms) {
return &ms[depIdx-len(es)] return &ms[depIdx-len(es)]
} else { } else {

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build !protolegacy
// +build !protolegacy // +build !protolegacy
package flags package flags

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build protolegacy
// +build protolegacy // +build protolegacy
package flags package flags

View File

@@ -12,6 +12,27 @@ import (
const File_google_protobuf_descriptor_proto = "google/protobuf/descriptor.proto" const File_google_protobuf_descriptor_proto = "google/protobuf/descriptor.proto"
// Full and short names for google.protobuf.Edition.
const (
Edition_enum_fullname = "google.protobuf.Edition"
Edition_enum_name = "Edition"
)
// Enum values for google.protobuf.Edition.
const (
Edition_EDITION_UNKNOWN_enum_value = 0
Edition_EDITION_PROTO2_enum_value = 998
Edition_EDITION_PROTO3_enum_value = 999
Edition_EDITION_2023_enum_value = 1000
Edition_EDITION_2024_enum_value = 1001
Edition_EDITION_1_TEST_ONLY_enum_value = 1
Edition_EDITION_2_TEST_ONLY_enum_value = 2
Edition_EDITION_99997_TEST_ONLY_enum_value = 99997
Edition_EDITION_99998_TEST_ONLY_enum_value = 99998
Edition_EDITION_99999_TEST_ONLY_enum_value = 99999
Edition_EDITION_MAX_enum_value = 2147483647
)
// Names for google.protobuf.FileDescriptorSet. // Names for google.protobuf.FileDescriptorSet.
const ( const (
FileDescriptorSet_message_name protoreflect.Name = "FileDescriptorSet" FileDescriptorSet_message_name protoreflect.Name = "FileDescriptorSet"
@@ -50,6 +71,7 @@ const (
FileDescriptorProto_Options_field_name protoreflect.Name = "options" FileDescriptorProto_Options_field_name protoreflect.Name = "options"
FileDescriptorProto_SourceCodeInfo_field_name protoreflect.Name = "source_code_info" FileDescriptorProto_SourceCodeInfo_field_name protoreflect.Name = "source_code_info"
FileDescriptorProto_Syntax_field_name protoreflect.Name = "syntax" FileDescriptorProto_Syntax_field_name protoreflect.Name = "syntax"
FileDescriptorProto_Edition_field_name protoreflect.Name = "edition"
FileDescriptorProto_Name_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.name" FileDescriptorProto_Name_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.name"
FileDescriptorProto_Package_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.package" FileDescriptorProto_Package_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.package"
@@ -63,6 +85,7 @@ const (
FileDescriptorProto_Options_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.options" FileDescriptorProto_Options_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.options"
FileDescriptorProto_SourceCodeInfo_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.source_code_info" FileDescriptorProto_SourceCodeInfo_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.source_code_info"
FileDescriptorProto_Syntax_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.syntax" FileDescriptorProto_Syntax_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.syntax"
FileDescriptorProto_Edition_field_fullname protoreflect.FullName = "google.protobuf.FileDescriptorProto.edition"
) )
// Field numbers for google.protobuf.FileDescriptorProto. // Field numbers for google.protobuf.FileDescriptorProto.
@@ -79,6 +102,7 @@ const (
FileDescriptorProto_Options_field_number protoreflect.FieldNumber = 8 FileDescriptorProto_Options_field_number protoreflect.FieldNumber = 8
FileDescriptorProto_SourceCodeInfo_field_number protoreflect.FieldNumber = 9 FileDescriptorProto_SourceCodeInfo_field_number protoreflect.FieldNumber = 9
FileDescriptorProto_Syntax_field_number protoreflect.FieldNumber = 12 FileDescriptorProto_Syntax_field_number protoreflect.FieldNumber = 12
FileDescriptorProto_Edition_field_number protoreflect.FieldNumber = 14
) )
// Names for google.protobuf.DescriptorProto. // Names for google.protobuf.DescriptorProto.
@@ -180,13 +204,64 @@ const (
// Field names for google.protobuf.ExtensionRangeOptions. // Field names for google.protobuf.ExtensionRangeOptions.
const ( const (
ExtensionRangeOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" ExtensionRangeOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
ExtensionRangeOptions_Declaration_field_name protoreflect.Name = "declaration"
ExtensionRangeOptions_Features_field_name protoreflect.Name = "features"
ExtensionRangeOptions_Verification_field_name protoreflect.Name = "verification"
ExtensionRangeOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.uninterpreted_option" ExtensionRangeOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.uninterpreted_option"
ExtensionRangeOptions_Declaration_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.declaration"
ExtensionRangeOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.features"
ExtensionRangeOptions_Verification_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.verification"
) )
// Field numbers for google.protobuf.ExtensionRangeOptions. // Field numbers for google.protobuf.ExtensionRangeOptions.
const ( const (
ExtensionRangeOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 ExtensionRangeOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
ExtensionRangeOptions_Declaration_field_number protoreflect.FieldNumber = 2
ExtensionRangeOptions_Features_field_number protoreflect.FieldNumber = 50
ExtensionRangeOptions_Verification_field_number protoreflect.FieldNumber = 3
)
// Full and short names for google.protobuf.ExtensionRangeOptions.VerificationState.
const (
ExtensionRangeOptions_VerificationState_enum_fullname = "google.protobuf.ExtensionRangeOptions.VerificationState"
ExtensionRangeOptions_VerificationState_enum_name = "VerificationState"
)
// Enum values for google.protobuf.ExtensionRangeOptions.VerificationState.
const (
ExtensionRangeOptions_DECLARATION_enum_value = 0
ExtensionRangeOptions_UNVERIFIED_enum_value = 1
)
// Names for google.protobuf.ExtensionRangeOptions.Declaration.
const (
ExtensionRangeOptions_Declaration_message_name protoreflect.Name = "Declaration"
ExtensionRangeOptions_Declaration_message_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration"
)
// Field names for google.protobuf.ExtensionRangeOptions.Declaration.
const (
ExtensionRangeOptions_Declaration_Number_field_name protoreflect.Name = "number"
ExtensionRangeOptions_Declaration_FullName_field_name protoreflect.Name = "full_name"
ExtensionRangeOptions_Declaration_Type_field_name protoreflect.Name = "type"
ExtensionRangeOptions_Declaration_Reserved_field_name protoreflect.Name = "reserved"
ExtensionRangeOptions_Declaration_Repeated_field_name protoreflect.Name = "repeated"
ExtensionRangeOptions_Declaration_Number_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration.number"
ExtensionRangeOptions_Declaration_FullName_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration.full_name"
ExtensionRangeOptions_Declaration_Type_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration.type"
ExtensionRangeOptions_Declaration_Reserved_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration.reserved"
ExtensionRangeOptions_Declaration_Repeated_field_fullname protoreflect.FullName = "google.protobuf.ExtensionRangeOptions.Declaration.repeated"
)
// Field numbers for google.protobuf.ExtensionRangeOptions.Declaration.
const (
ExtensionRangeOptions_Declaration_Number_field_number protoreflect.FieldNumber = 1
ExtensionRangeOptions_Declaration_FullName_field_number protoreflect.FieldNumber = 2
ExtensionRangeOptions_Declaration_Type_field_number protoreflect.FieldNumber = 3
ExtensionRangeOptions_Declaration_Reserved_field_number protoreflect.FieldNumber = 5
ExtensionRangeOptions_Declaration_Repeated_field_number protoreflect.FieldNumber = 6
) )
// Names for google.protobuf.FieldDescriptorProto. // Names for google.protobuf.FieldDescriptorProto.
@@ -243,12 +318,41 @@ const (
FieldDescriptorProto_Type_enum_name = "Type" FieldDescriptorProto_Type_enum_name = "Type"
) )
// Enum values for google.protobuf.FieldDescriptorProto.Type.
const (
FieldDescriptorProto_TYPE_DOUBLE_enum_value = 1
FieldDescriptorProto_TYPE_FLOAT_enum_value = 2
FieldDescriptorProto_TYPE_INT64_enum_value = 3
FieldDescriptorProto_TYPE_UINT64_enum_value = 4
FieldDescriptorProto_TYPE_INT32_enum_value = 5
FieldDescriptorProto_TYPE_FIXED64_enum_value = 6
FieldDescriptorProto_TYPE_FIXED32_enum_value = 7
FieldDescriptorProto_TYPE_BOOL_enum_value = 8
FieldDescriptorProto_TYPE_STRING_enum_value = 9
FieldDescriptorProto_TYPE_GROUP_enum_value = 10
FieldDescriptorProto_TYPE_MESSAGE_enum_value = 11
FieldDescriptorProto_TYPE_BYTES_enum_value = 12
FieldDescriptorProto_TYPE_UINT32_enum_value = 13
FieldDescriptorProto_TYPE_ENUM_enum_value = 14
FieldDescriptorProto_TYPE_SFIXED32_enum_value = 15
FieldDescriptorProto_TYPE_SFIXED64_enum_value = 16
FieldDescriptorProto_TYPE_SINT32_enum_value = 17
FieldDescriptorProto_TYPE_SINT64_enum_value = 18
)
// Full and short names for google.protobuf.FieldDescriptorProto.Label. // Full and short names for google.protobuf.FieldDescriptorProto.Label.
const ( const (
FieldDescriptorProto_Label_enum_fullname = "google.protobuf.FieldDescriptorProto.Label" FieldDescriptorProto_Label_enum_fullname = "google.protobuf.FieldDescriptorProto.Label"
FieldDescriptorProto_Label_enum_name = "Label" FieldDescriptorProto_Label_enum_name = "Label"
) )
// Enum values for google.protobuf.FieldDescriptorProto.Label.
const (
FieldDescriptorProto_LABEL_OPTIONAL_enum_value = 1
FieldDescriptorProto_LABEL_REPEATED_enum_value = 3
FieldDescriptorProto_LABEL_REQUIRED_enum_value = 2
)
// Names for google.protobuf.OneofDescriptorProto. // Names for google.protobuf.OneofDescriptorProto.
const ( const (
OneofDescriptorProto_message_name protoreflect.Name = "OneofDescriptorProto" OneofDescriptorProto_message_name protoreflect.Name = "OneofDescriptorProto"
@@ -420,7 +524,6 @@ const (
FileOptions_CcGenericServices_field_name protoreflect.Name = "cc_generic_services" FileOptions_CcGenericServices_field_name protoreflect.Name = "cc_generic_services"
FileOptions_JavaGenericServices_field_name protoreflect.Name = "java_generic_services" FileOptions_JavaGenericServices_field_name protoreflect.Name = "java_generic_services"
FileOptions_PyGenericServices_field_name protoreflect.Name = "py_generic_services" FileOptions_PyGenericServices_field_name protoreflect.Name = "py_generic_services"
FileOptions_PhpGenericServices_field_name protoreflect.Name = "php_generic_services"
FileOptions_Deprecated_field_name protoreflect.Name = "deprecated" FileOptions_Deprecated_field_name protoreflect.Name = "deprecated"
FileOptions_CcEnableArenas_field_name protoreflect.Name = "cc_enable_arenas" FileOptions_CcEnableArenas_field_name protoreflect.Name = "cc_enable_arenas"
FileOptions_ObjcClassPrefix_field_name protoreflect.Name = "objc_class_prefix" FileOptions_ObjcClassPrefix_field_name protoreflect.Name = "objc_class_prefix"
@@ -430,6 +533,7 @@ const (
FileOptions_PhpNamespace_field_name protoreflect.Name = "php_namespace" FileOptions_PhpNamespace_field_name protoreflect.Name = "php_namespace"
FileOptions_PhpMetadataNamespace_field_name protoreflect.Name = "php_metadata_namespace" FileOptions_PhpMetadataNamespace_field_name protoreflect.Name = "php_metadata_namespace"
FileOptions_RubyPackage_field_name protoreflect.Name = "ruby_package" FileOptions_RubyPackage_field_name protoreflect.Name = "ruby_package"
FileOptions_Features_field_name protoreflect.Name = "features"
FileOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" FileOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
FileOptions_JavaPackage_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.java_package" FileOptions_JavaPackage_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.java_package"
@@ -442,7 +546,6 @@ const (
FileOptions_CcGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.cc_generic_services" FileOptions_CcGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.cc_generic_services"
FileOptions_JavaGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.java_generic_services" FileOptions_JavaGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.java_generic_services"
FileOptions_PyGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.py_generic_services" FileOptions_PyGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.py_generic_services"
FileOptions_PhpGenericServices_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.php_generic_services"
FileOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.deprecated" FileOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.deprecated"
FileOptions_CcEnableArenas_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.cc_enable_arenas" FileOptions_CcEnableArenas_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.cc_enable_arenas"
FileOptions_ObjcClassPrefix_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.objc_class_prefix" FileOptions_ObjcClassPrefix_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.objc_class_prefix"
@@ -452,6 +555,7 @@ const (
FileOptions_PhpNamespace_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.php_namespace" FileOptions_PhpNamespace_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.php_namespace"
FileOptions_PhpMetadataNamespace_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.php_metadata_namespace" FileOptions_PhpMetadataNamespace_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.php_metadata_namespace"
FileOptions_RubyPackage_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.ruby_package" FileOptions_RubyPackage_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.ruby_package"
FileOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.features"
FileOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.uninterpreted_option" FileOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.FileOptions.uninterpreted_option"
) )
@@ -467,7 +571,6 @@ const (
FileOptions_CcGenericServices_field_number protoreflect.FieldNumber = 16 FileOptions_CcGenericServices_field_number protoreflect.FieldNumber = 16
FileOptions_JavaGenericServices_field_number protoreflect.FieldNumber = 17 FileOptions_JavaGenericServices_field_number protoreflect.FieldNumber = 17
FileOptions_PyGenericServices_field_number protoreflect.FieldNumber = 18 FileOptions_PyGenericServices_field_number protoreflect.FieldNumber = 18
FileOptions_PhpGenericServices_field_number protoreflect.FieldNumber = 42
FileOptions_Deprecated_field_number protoreflect.FieldNumber = 23 FileOptions_Deprecated_field_number protoreflect.FieldNumber = 23
FileOptions_CcEnableArenas_field_number protoreflect.FieldNumber = 31 FileOptions_CcEnableArenas_field_number protoreflect.FieldNumber = 31
FileOptions_ObjcClassPrefix_field_number protoreflect.FieldNumber = 36 FileOptions_ObjcClassPrefix_field_number protoreflect.FieldNumber = 36
@@ -477,6 +580,7 @@ const (
FileOptions_PhpNamespace_field_number protoreflect.FieldNumber = 41 FileOptions_PhpNamespace_field_number protoreflect.FieldNumber = 41
FileOptions_PhpMetadataNamespace_field_number protoreflect.FieldNumber = 44 FileOptions_PhpMetadataNamespace_field_number protoreflect.FieldNumber = 44
FileOptions_RubyPackage_field_number protoreflect.FieldNumber = 45 FileOptions_RubyPackage_field_number protoreflect.FieldNumber = 45
FileOptions_Features_field_number protoreflect.FieldNumber = 50
FileOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 FileOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -486,6 +590,13 @@ const (
FileOptions_OptimizeMode_enum_name = "OptimizeMode" FileOptions_OptimizeMode_enum_name = "OptimizeMode"
) )
// Enum values for google.protobuf.FileOptions.OptimizeMode.
const (
FileOptions_SPEED_enum_value = 1
FileOptions_CODE_SIZE_enum_value = 2
FileOptions_LITE_RUNTIME_enum_value = 3
)
// Names for google.protobuf.MessageOptions. // Names for google.protobuf.MessageOptions.
const ( const (
MessageOptions_message_name protoreflect.Name = "MessageOptions" MessageOptions_message_name protoreflect.Name = "MessageOptions"
@@ -498,12 +609,16 @@ const (
MessageOptions_NoStandardDescriptorAccessor_field_name protoreflect.Name = "no_standard_descriptor_accessor" MessageOptions_NoStandardDescriptorAccessor_field_name protoreflect.Name = "no_standard_descriptor_accessor"
MessageOptions_Deprecated_field_name protoreflect.Name = "deprecated" MessageOptions_Deprecated_field_name protoreflect.Name = "deprecated"
MessageOptions_MapEntry_field_name protoreflect.Name = "map_entry" MessageOptions_MapEntry_field_name protoreflect.Name = "map_entry"
MessageOptions_DeprecatedLegacyJsonFieldConflicts_field_name protoreflect.Name = "deprecated_legacy_json_field_conflicts"
MessageOptions_Features_field_name protoreflect.Name = "features"
MessageOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" MessageOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
MessageOptions_MessageSetWireFormat_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.message_set_wire_format" MessageOptions_MessageSetWireFormat_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.message_set_wire_format"
MessageOptions_NoStandardDescriptorAccessor_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.no_standard_descriptor_accessor" MessageOptions_NoStandardDescriptorAccessor_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.no_standard_descriptor_accessor"
MessageOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.deprecated" MessageOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.deprecated"
MessageOptions_MapEntry_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.map_entry" MessageOptions_MapEntry_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.map_entry"
MessageOptions_DeprecatedLegacyJsonFieldConflicts_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.deprecated_legacy_json_field_conflicts"
MessageOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.features"
MessageOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.uninterpreted_option" MessageOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.MessageOptions.uninterpreted_option"
) )
@@ -513,6 +628,8 @@ const (
MessageOptions_NoStandardDescriptorAccessor_field_number protoreflect.FieldNumber = 2 MessageOptions_NoStandardDescriptorAccessor_field_number protoreflect.FieldNumber = 2
MessageOptions_Deprecated_field_number protoreflect.FieldNumber = 3 MessageOptions_Deprecated_field_number protoreflect.FieldNumber = 3
MessageOptions_MapEntry_field_number protoreflect.FieldNumber = 7 MessageOptions_MapEntry_field_number protoreflect.FieldNumber = 7
MessageOptions_DeprecatedLegacyJsonFieldConflicts_field_number protoreflect.FieldNumber = 11
MessageOptions_Features_field_number protoreflect.FieldNumber = 12
MessageOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 MessageOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -528,16 +645,28 @@ const (
FieldOptions_Packed_field_name protoreflect.Name = "packed" FieldOptions_Packed_field_name protoreflect.Name = "packed"
FieldOptions_Jstype_field_name protoreflect.Name = "jstype" FieldOptions_Jstype_field_name protoreflect.Name = "jstype"
FieldOptions_Lazy_field_name protoreflect.Name = "lazy" FieldOptions_Lazy_field_name protoreflect.Name = "lazy"
FieldOptions_UnverifiedLazy_field_name protoreflect.Name = "unverified_lazy"
FieldOptions_Deprecated_field_name protoreflect.Name = "deprecated" FieldOptions_Deprecated_field_name protoreflect.Name = "deprecated"
FieldOptions_Weak_field_name protoreflect.Name = "weak" FieldOptions_Weak_field_name protoreflect.Name = "weak"
FieldOptions_DebugRedact_field_name protoreflect.Name = "debug_redact"
FieldOptions_Retention_field_name protoreflect.Name = "retention"
FieldOptions_Targets_field_name protoreflect.Name = "targets"
FieldOptions_EditionDefaults_field_name protoreflect.Name = "edition_defaults"
FieldOptions_Features_field_name protoreflect.Name = "features"
FieldOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" FieldOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
FieldOptions_Ctype_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.ctype" FieldOptions_Ctype_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.ctype"
FieldOptions_Packed_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.packed" FieldOptions_Packed_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.packed"
FieldOptions_Jstype_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.jstype" FieldOptions_Jstype_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.jstype"
FieldOptions_Lazy_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.lazy" FieldOptions_Lazy_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.lazy"
FieldOptions_UnverifiedLazy_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.unverified_lazy"
FieldOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.deprecated" FieldOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.deprecated"
FieldOptions_Weak_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.weak" FieldOptions_Weak_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.weak"
FieldOptions_DebugRedact_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.debug_redact"
FieldOptions_Retention_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.retention"
FieldOptions_Targets_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.targets"
FieldOptions_EditionDefaults_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.edition_defaults"
FieldOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.features"
FieldOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.uninterpreted_option" FieldOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.uninterpreted_option"
) )
@@ -547,8 +676,14 @@ const (
FieldOptions_Packed_field_number protoreflect.FieldNumber = 2 FieldOptions_Packed_field_number protoreflect.FieldNumber = 2
FieldOptions_Jstype_field_number protoreflect.FieldNumber = 6 FieldOptions_Jstype_field_number protoreflect.FieldNumber = 6
FieldOptions_Lazy_field_number protoreflect.FieldNumber = 5 FieldOptions_Lazy_field_number protoreflect.FieldNumber = 5
FieldOptions_UnverifiedLazy_field_number protoreflect.FieldNumber = 15
FieldOptions_Deprecated_field_number protoreflect.FieldNumber = 3 FieldOptions_Deprecated_field_number protoreflect.FieldNumber = 3
FieldOptions_Weak_field_number protoreflect.FieldNumber = 10 FieldOptions_Weak_field_number protoreflect.FieldNumber = 10
FieldOptions_DebugRedact_field_number protoreflect.FieldNumber = 16
FieldOptions_Retention_field_number protoreflect.FieldNumber = 17
FieldOptions_Targets_field_number protoreflect.FieldNumber = 19
FieldOptions_EditionDefaults_field_number protoreflect.FieldNumber = 20
FieldOptions_Features_field_number protoreflect.FieldNumber = 21
FieldOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 FieldOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -558,12 +693,80 @@ const (
FieldOptions_CType_enum_name = "CType" FieldOptions_CType_enum_name = "CType"
) )
// Enum values for google.protobuf.FieldOptions.CType.
const (
FieldOptions_STRING_enum_value = 0
FieldOptions_CORD_enum_value = 1
FieldOptions_STRING_PIECE_enum_value = 2
)
// Full and short names for google.protobuf.FieldOptions.JSType. // Full and short names for google.protobuf.FieldOptions.JSType.
const ( const (
FieldOptions_JSType_enum_fullname = "google.protobuf.FieldOptions.JSType" FieldOptions_JSType_enum_fullname = "google.protobuf.FieldOptions.JSType"
FieldOptions_JSType_enum_name = "JSType" FieldOptions_JSType_enum_name = "JSType"
) )
// Enum values for google.protobuf.FieldOptions.JSType.
const (
FieldOptions_JS_NORMAL_enum_value = 0
FieldOptions_JS_STRING_enum_value = 1
FieldOptions_JS_NUMBER_enum_value = 2
)
// Full and short names for google.protobuf.FieldOptions.OptionRetention.
const (
FieldOptions_OptionRetention_enum_fullname = "google.protobuf.FieldOptions.OptionRetention"
FieldOptions_OptionRetention_enum_name = "OptionRetention"
)
// Enum values for google.protobuf.FieldOptions.OptionRetention.
const (
FieldOptions_RETENTION_UNKNOWN_enum_value = 0
FieldOptions_RETENTION_RUNTIME_enum_value = 1
FieldOptions_RETENTION_SOURCE_enum_value = 2
)
// Full and short names for google.protobuf.FieldOptions.OptionTargetType.
const (
FieldOptions_OptionTargetType_enum_fullname = "google.protobuf.FieldOptions.OptionTargetType"
FieldOptions_OptionTargetType_enum_name = "OptionTargetType"
)
// Enum values for google.protobuf.FieldOptions.OptionTargetType.
const (
FieldOptions_TARGET_TYPE_UNKNOWN_enum_value = 0
FieldOptions_TARGET_TYPE_FILE_enum_value = 1
FieldOptions_TARGET_TYPE_EXTENSION_RANGE_enum_value = 2
FieldOptions_TARGET_TYPE_MESSAGE_enum_value = 3
FieldOptions_TARGET_TYPE_FIELD_enum_value = 4
FieldOptions_TARGET_TYPE_ONEOF_enum_value = 5
FieldOptions_TARGET_TYPE_ENUM_enum_value = 6
FieldOptions_TARGET_TYPE_ENUM_ENTRY_enum_value = 7
FieldOptions_TARGET_TYPE_SERVICE_enum_value = 8
FieldOptions_TARGET_TYPE_METHOD_enum_value = 9
)
// Names for google.protobuf.FieldOptions.EditionDefault.
const (
FieldOptions_EditionDefault_message_name protoreflect.Name = "EditionDefault"
FieldOptions_EditionDefault_message_fullname protoreflect.FullName = "google.protobuf.FieldOptions.EditionDefault"
)
// Field names for google.protobuf.FieldOptions.EditionDefault.
const (
FieldOptions_EditionDefault_Edition_field_name protoreflect.Name = "edition"
FieldOptions_EditionDefault_Value_field_name protoreflect.Name = "value"
FieldOptions_EditionDefault_Edition_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.EditionDefault.edition"
FieldOptions_EditionDefault_Value_field_fullname protoreflect.FullName = "google.protobuf.FieldOptions.EditionDefault.value"
)
// Field numbers for google.protobuf.FieldOptions.EditionDefault.
const (
FieldOptions_EditionDefault_Edition_field_number protoreflect.FieldNumber = 3
FieldOptions_EditionDefault_Value_field_number protoreflect.FieldNumber = 2
)
// Names for google.protobuf.OneofOptions. // Names for google.protobuf.OneofOptions.
const ( const (
OneofOptions_message_name protoreflect.Name = "OneofOptions" OneofOptions_message_name protoreflect.Name = "OneofOptions"
@@ -572,13 +775,16 @@ const (
// Field names for google.protobuf.OneofOptions. // Field names for google.protobuf.OneofOptions.
const ( const (
OneofOptions_Features_field_name protoreflect.Name = "features"
OneofOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" OneofOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
OneofOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.OneofOptions.features"
OneofOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.OneofOptions.uninterpreted_option" OneofOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.OneofOptions.uninterpreted_option"
) )
// Field numbers for google.protobuf.OneofOptions. // Field numbers for google.protobuf.OneofOptions.
const ( const (
OneofOptions_Features_field_number protoreflect.FieldNumber = 1
OneofOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 OneofOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -592,10 +798,14 @@ const (
const ( const (
EnumOptions_AllowAlias_field_name protoreflect.Name = "allow_alias" EnumOptions_AllowAlias_field_name protoreflect.Name = "allow_alias"
EnumOptions_Deprecated_field_name protoreflect.Name = "deprecated" EnumOptions_Deprecated_field_name protoreflect.Name = "deprecated"
EnumOptions_DeprecatedLegacyJsonFieldConflicts_field_name protoreflect.Name = "deprecated_legacy_json_field_conflicts"
EnumOptions_Features_field_name protoreflect.Name = "features"
EnumOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" EnumOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
EnumOptions_AllowAlias_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.allow_alias" EnumOptions_AllowAlias_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.allow_alias"
EnumOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.deprecated" EnumOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.deprecated"
EnumOptions_DeprecatedLegacyJsonFieldConflicts_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.deprecated_legacy_json_field_conflicts"
EnumOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.features"
EnumOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.uninterpreted_option" EnumOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.EnumOptions.uninterpreted_option"
) )
@@ -603,6 +813,8 @@ const (
const ( const (
EnumOptions_AllowAlias_field_number protoreflect.FieldNumber = 2 EnumOptions_AllowAlias_field_number protoreflect.FieldNumber = 2
EnumOptions_Deprecated_field_number protoreflect.FieldNumber = 3 EnumOptions_Deprecated_field_number protoreflect.FieldNumber = 3
EnumOptions_DeprecatedLegacyJsonFieldConflicts_field_number protoreflect.FieldNumber = 6
EnumOptions_Features_field_number protoreflect.FieldNumber = 7
EnumOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 EnumOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -615,15 +827,21 @@ const (
// Field names for google.protobuf.EnumValueOptions. // Field names for google.protobuf.EnumValueOptions.
const ( const (
EnumValueOptions_Deprecated_field_name protoreflect.Name = "deprecated" EnumValueOptions_Deprecated_field_name protoreflect.Name = "deprecated"
EnumValueOptions_Features_field_name protoreflect.Name = "features"
EnumValueOptions_DebugRedact_field_name protoreflect.Name = "debug_redact"
EnumValueOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" EnumValueOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
EnumValueOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.deprecated" EnumValueOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.deprecated"
EnumValueOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.features"
EnumValueOptions_DebugRedact_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.debug_redact"
EnumValueOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.uninterpreted_option" EnumValueOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.EnumValueOptions.uninterpreted_option"
) )
// Field numbers for google.protobuf.EnumValueOptions. // Field numbers for google.protobuf.EnumValueOptions.
const ( const (
EnumValueOptions_Deprecated_field_number protoreflect.FieldNumber = 1 EnumValueOptions_Deprecated_field_number protoreflect.FieldNumber = 1
EnumValueOptions_Features_field_number protoreflect.FieldNumber = 2
EnumValueOptions_DebugRedact_field_number protoreflect.FieldNumber = 3
EnumValueOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 EnumValueOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -635,15 +853,18 @@ const (
// Field names for google.protobuf.ServiceOptions. // Field names for google.protobuf.ServiceOptions.
const ( const (
ServiceOptions_Features_field_name protoreflect.Name = "features"
ServiceOptions_Deprecated_field_name protoreflect.Name = "deprecated" ServiceOptions_Deprecated_field_name protoreflect.Name = "deprecated"
ServiceOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" ServiceOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
ServiceOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.ServiceOptions.features"
ServiceOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.ServiceOptions.deprecated" ServiceOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.ServiceOptions.deprecated"
ServiceOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.ServiceOptions.uninterpreted_option" ServiceOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.ServiceOptions.uninterpreted_option"
) )
// Field numbers for google.protobuf.ServiceOptions. // Field numbers for google.protobuf.ServiceOptions.
const ( const (
ServiceOptions_Features_field_number protoreflect.FieldNumber = 34
ServiceOptions_Deprecated_field_number protoreflect.FieldNumber = 33 ServiceOptions_Deprecated_field_number protoreflect.FieldNumber = 33
ServiceOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 ServiceOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -658,10 +879,12 @@ const (
const ( const (
MethodOptions_Deprecated_field_name protoreflect.Name = "deprecated" MethodOptions_Deprecated_field_name protoreflect.Name = "deprecated"
MethodOptions_IdempotencyLevel_field_name protoreflect.Name = "idempotency_level" MethodOptions_IdempotencyLevel_field_name protoreflect.Name = "idempotency_level"
MethodOptions_Features_field_name protoreflect.Name = "features"
MethodOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option" MethodOptions_UninterpretedOption_field_name protoreflect.Name = "uninterpreted_option"
MethodOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.deprecated" MethodOptions_Deprecated_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.deprecated"
MethodOptions_IdempotencyLevel_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.idempotency_level" MethodOptions_IdempotencyLevel_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.idempotency_level"
MethodOptions_Features_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.features"
MethodOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.uninterpreted_option" MethodOptions_UninterpretedOption_field_fullname protoreflect.FullName = "google.protobuf.MethodOptions.uninterpreted_option"
) )
@@ -669,6 +892,7 @@ const (
const ( const (
MethodOptions_Deprecated_field_number protoreflect.FieldNumber = 33 MethodOptions_Deprecated_field_number protoreflect.FieldNumber = 33
MethodOptions_IdempotencyLevel_field_number protoreflect.FieldNumber = 34 MethodOptions_IdempotencyLevel_field_number protoreflect.FieldNumber = 34
MethodOptions_Features_field_number protoreflect.FieldNumber = 35
MethodOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999 MethodOptions_UninterpretedOption_field_number protoreflect.FieldNumber = 999
) )
@@ -678,6 +902,13 @@ const (
MethodOptions_IdempotencyLevel_enum_name = "IdempotencyLevel" MethodOptions_IdempotencyLevel_enum_name = "IdempotencyLevel"
) )
// Enum values for google.protobuf.MethodOptions.IdempotencyLevel.
const (
MethodOptions_IDEMPOTENCY_UNKNOWN_enum_value = 0
MethodOptions_NO_SIDE_EFFECTS_enum_value = 1
MethodOptions_IDEMPOTENT_enum_value = 2
)
// Names for google.protobuf.UninterpretedOption. // Names for google.protobuf.UninterpretedOption.
const ( const (
UninterpretedOption_message_name protoreflect.Name = "UninterpretedOption" UninterpretedOption_message_name protoreflect.Name = "UninterpretedOption"
@@ -735,6 +966,163 @@ const (
UninterpretedOption_NamePart_IsExtension_field_number protoreflect.FieldNumber = 2 UninterpretedOption_NamePart_IsExtension_field_number protoreflect.FieldNumber = 2
) )
// Names for google.protobuf.FeatureSet.
const (
FeatureSet_message_name protoreflect.Name = "FeatureSet"
FeatureSet_message_fullname protoreflect.FullName = "google.protobuf.FeatureSet"
)
// Field names for google.protobuf.FeatureSet.
const (
FeatureSet_FieldPresence_field_name protoreflect.Name = "field_presence"
FeatureSet_EnumType_field_name protoreflect.Name = "enum_type"
FeatureSet_RepeatedFieldEncoding_field_name protoreflect.Name = "repeated_field_encoding"
FeatureSet_Utf8Validation_field_name protoreflect.Name = "utf8_validation"
FeatureSet_MessageEncoding_field_name protoreflect.Name = "message_encoding"
FeatureSet_JsonFormat_field_name protoreflect.Name = "json_format"
FeatureSet_FieldPresence_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.field_presence"
FeatureSet_EnumType_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.enum_type"
FeatureSet_RepeatedFieldEncoding_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.repeated_field_encoding"
FeatureSet_Utf8Validation_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.utf8_validation"
FeatureSet_MessageEncoding_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.message_encoding"
FeatureSet_JsonFormat_field_fullname protoreflect.FullName = "google.protobuf.FeatureSet.json_format"
)
// Field numbers for google.protobuf.FeatureSet.
const (
FeatureSet_FieldPresence_field_number protoreflect.FieldNumber = 1
FeatureSet_EnumType_field_number protoreflect.FieldNumber = 2
FeatureSet_RepeatedFieldEncoding_field_number protoreflect.FieldNumber = 3
FeatureSet_Utf8Validation_field_number protoreflect.FieldNumber = 4
FeatureSet_MessageEncoding_field_number protoreflect.FieldNumber = 5
FeatureSet_JsonFormat_field_number protoreflect.FieldNumber = 6
)
// Full and short names for google.protobuf.FeatureSet.FieldPresence.
const (
FeatureSet_FieldPresence_enum_fullname = "google.protobuf.FeatureSet.FieldPresence"
FeatureSet_FieldPresence_enum_name = "FieldPresence"
)
// Enum values for google.protobuf.FeatureSet.FieldPresence.
const (
FeatureSet_FIELD_PRESENCE_UNKNOWN_enum_value = 0
FeatureSet_EXPLICIT_enum_value = 1
FeatureSet_IMPLICIT_enum_value = 2
FeatureSet_LEGACY_REQUIRED_enum_value = 3
)
// Full and short names for google.protobuf.FeatureSet.EnumType.
const (
FeatureSet_EnumType_enum_fullname = "google.protobuf.FeatureSet.EnumType"
FeatureSet_EnumType_enum_name = "EnumType"
)
// Enum values for google.protobuf.FeatureSet.EnumType.
const (
FeatureSet_ENUM_TYPE_UNKNOWN_enum_value = 0
FeatureSet_OPEN_enum_value = 1
FeatureSet_CLOSED_enum_value = 2
)
// Full and short names for google.protobuf.FeatureSet.RepeatedFieldEncoding.
const (
FeatureSet_RepeatedFieldEncoding_enum_fullname = "google.protobuf.FeatureSet.RepeatedFieldEncoding"
FeatureSet_RepeatedFieldEncoding_enum_name = "RepeatedFieldEncoding"
)
// Enum values for google.protobuf.FeatureSet.RepeatedFieldEncoding.
const (
FeatureSet_REPEATED_FIELD_ENCODING_UNKNOWN_enum_value = 0
FeatureSet_PACKED_enum_value = 1
FeatureSet_EXPANDED_enum_value = 2
)
// Full and short names for google.protobuf.FeatureSet.Utf8Validation.
const (
FeatureSet_Utf8Validation_enum_fullname = "google.protobuf.FeatureSet.Utf8Validation"
FeatureSet_Utf8Validation_enum_name = "Utf8Validation"
)
// Enum values for google.protobuf.FeatureSet.Utf8Validation.
const (
FeatureSet_UTF8_VALIDATION_UNKNOWN_enum_value = 0
FeatureSet_VERIFY_enum_value = 2
FeatureSet_NONE_enum_value = 3
)
// Full and short names for google.protobuf.FeatureSet.MessageEncoding.
const (
FeatureSet_MessageEncoding_enum_fullname = "google.protobuf.FeatureSet.MessageEncoding"
FeatureSet_MessageEncoding_enum_name = "MessageEncoding"
)
// Enum values for google.protobuf.FeatureSet.MessageEncoding.
const (
FeatureSet_MESSAGE_ENCODING_UNKNOWN_enum_value = 0
FeatureSet_LENGTH_PREFIXED_enum_value = 1
FeatureSet_DELIMITED_enum_value = 2
)
// Full and short names for google.protobuf.FeatureSet.JsonFormat.
const (
FeatureSet_JsonFormat_enum_fullname = "google.protobuf.FeatureSet.JsonFormat"
FeatureSet_JsonFormat_enum_name = "JsonFormat"
)
// Enum values for google.protobuf.FeatureSet.JsonFormat.
const (
FeatureSet_JSON_FORMAT_UNKNOWN_enum_value = 0
FeatureSet_ALLOW_enum_value = 1
FeatureSet_LEGACY_BEST_EFFORT_enum_value = 2
)
// Names for google.protobuf.FeatureSetDefaults.
const (
FeatureSetDefaults_message_name protoreflect.Name = "FeatureSetDefaults"
FeatureSetDefaults_message_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults"
)
// Field names for google.protobuf.FeatureSetDefaults.
const (
FeatureSetDefaults_Defaults_field_name protoreflect.Name = "defaults"
FeatureSetDefaults_MinimumEdition_field_name protoreflect.Name = "minimum_edition"
FeatureSetDefaults_MaximumEdition_field_name protoreflect.Name = "maximum_edition"
FeatureSetDefaults_Defaults_field_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.defaults"
FeatureSetDefaults_MinimumEdition_field_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.minimum_edition"
FeatureSetDefaults_MaximumEdition_field_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.maximum_edition"
)
// Field numbers for google.protobuf.FeatureSetDefaults.
const (
FeatureSetDefaults_Defaults_field_number protoreflect.FieldNumber = 1
FeatureSetDefaults_MinimumEdition_field_number protoreflect.FieldNumber = 4
FeatureSetDefaults_MaximumEdition_field_number protoreflect.FieldNumber = 5
)
// Names for google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault.
const (
FeatureSetDefaults_FeatureSetEditionDefault_message_name protoreflect.Name = "FeatureSetEditionDefault"
FeatureSetDefaults_FeatureSetEditionDefault_message_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault"
)
// Field names for google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault.
const (
FeatureSetDefaults_FeatureSetEditionDefault_Edition_field_name protoreflect.Name = "edition"
FeatureSetDefaults_FeatureSetEditionDefault_Features_field_name protoreflect.Name = "features"
FeatureSetDefaults_FeatureSetEditionDefault_Edition_field_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault.edition"
FeatureSetDefaults_FeatureSetEditionDefault_Features_field_fullname protoreflect.FullName = "google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault.features"
)
// Field numbers for google.protobuf.FeatureSetDefaults.FeatureSetEditionDefault.
const (
FeatureSetDefaults_FeatureSetEditionDefault_Edition_field_number protoreflect.FieldNumber = 3
FeatureSetDefaults_FeatureSetEditionDefault_Features_field_number protoreflect.FieldNumber = 2
)
// Names for google.protobuf.SourceCodeInfo. // Names for google.protobuf.SourceCodeInfo.
const ( const (
SourceCodeInfo_message_name protoreflect.Name = "SourceCodeInfo" SourceCodeInfo_message_name protoreflect.Name = "SourceCodeInfo"
@@ -813,11 +1201,13 @@ const (
GeneratedCodeInfo_Annotation_SourceFile_field_name protoreflect.Name = "source_file" GeneratedCodeInfo_Annotation_SourceFile_field_name protoreflect.Name = "source_file"
GeneratedCodeInfo_Annotation_Begin_field_name protoreflect.Name = "begin" GeneratedCodeInfo_Annotation_Begin_field_name protoreflect.Name = "begin"
GeneratedCodeInfo_Annotation_End_field_name protoreflect.Name = "end" GeneratedCodeInfo_Annotation_End_field_name protoreflect.Name = "end"
GeneratedCodeInfo_Annotation_Semantic_field_name protoreflect.Name = "semantic"
GeneratedCodeInfo_Annotation_Path_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.path" GeneratedCodeInfo_Annotation_Path_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.path"
GeneratedCodeInfo_Annotation_SourceFile_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.source_file" GeneratedCodeInfo_Annotation_SourceFile_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.source_file"
GeneratedCodeInfo_Annotation_Begin_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.begin" GeneratedCodeInfo_Annotation_Begin_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.begin"
GeneratedCodeInfo_Annotation_End_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.end" GeneratedCodeInfo_Annotation_End_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.end"
GeneratedCodeInfo_Annotation_Semantic_field_fullname protoreflect.FullName = "google.protobuf.GeneratedCodeInfo.Annotation.semantic"
) )
// Field numbers for google.protobuf.GeneratedCodeInfo.Annotation. // Field numbers for google.protobuf.GeneratedCodeInfo.Annotation.
@@ -826,4 +1216,18 @@ const (
GeneratedCodeInfo_Annotation_SourceFile_field_number protoreflect.FieldNumber = 2 GeneratedCodeInfo_Annotation_SourceFile_field_number protoreflect.FieldNumber = 2
GeneratedCodeInfo_Annotation_Begin_field_number protoreflect.FieldNumber = 3 GeneratedCodeInfo_Annotation_Begin_field_number protoreflect.FieldNumber = 3
GeneratedCodeInfo_Annotation_End_field_number protoreflect.FieldNumber = 4 GeneratedCodeInfo_Annotation_End_field_number protoreflect.FieldNumber = 4
GeneratedCodeInfo_Annotation_Semantic_field_number protoreflect.FieldNumber = 5
)
// Full and short names for google.protobuf.GeneratedCodeInfo.Annotation.Semantic.
const (
GeneratedCodeInfo_Annotation_Semantic_enum_fullname = "google.protobuf.GeneratedCodeInfo.Annotation.Semantic"
GeneratedCodeInfo_Annotation_Semantic_enum_name = "Semantic"
)
// Enum values for google.protobuf.GeneratedCodeInfo.Annotation.Semantic.
const (
GeneratedCodeInfo_Annotation_NONE_enum_value = 0
GeneratedCodeInfo_Annotation_SET_enum_value = 1
GeneratedCodeInfo_Annotation_ALIAS_enum_value = 2
) )

View File

@@ -0,0 +1,31 @@
// Copyright 2019 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Code generated by generate-protos. DO NOT EDIT.
package genid
import (
protoreflect "google.golang.org/protobuf/reflect/protoreflect"
)
const File_reflect_protodesc_proto_go_features_proto = "reflect/protodesc/proto/go_features.proto"
// Names for google.protobuf.GoFeatures.
const (
GoFeatures_message_name protoreflect.Name = "GoFeatures"
GoFeatures_message_fullname protoreflect.FullName = "google.protobuf.GoFeatures"
)
// Field names for google.protobuf.GoFeatures.
const (
GoFeatures_LegacyUnmarshalJsonEnum_field_name protoreflect.Name = "legacy_unmarshal_json_enum"
GoFeatures_LegacyUnmarshalJsonEnum_field_fullname protoreflect.FullName = "google.protobuf.GoFeatures.legacy_unmarshal_json_enum"
)
// Field numbers for google.protobuf.GoFeatures.
const (
GoFeatures_LegacyUnmarshalJsonEnum_field_number protoreflect.FieldNumber = 1
)

View File

@@ -18,6 +18,11 @@ const (
NullValue_enum_name = "NullValue" NullValue_enum_name = "NullValue"
) )
// Enum values for google.protobuf.NullValue.
const (
NullValue_NULL_VALUE_enum_value = 0
)
// Names for google.protobuf.Struct. // Names for google.protobuf.Struct.
const ( const (
Struct_message_name protoreflect.Name = "Struct" Struct_message_name protoreflect.Name = "Struct"

View File

@@ -18,6 +18,13 @@ const (
Syntax_enum_name = "Syntax" Syntax_enum_name = "Syntax"
) )
// Enum values for google.protobuf.Syntax.
const (
Syntax_SYNTAX_PROTO2_enum_value = 0
Syntax_SYNTAX_PROTO3_enum_value = 1
Syntax_SYNTAX_EDITIONS_enum_value = 2
)
// Names for google.protobuf.Type. // Names for google.protobuf.Type.
const ( const (
Type_message_name protoreflect.Name = "Type" Type_message_name protoreflect.Name = "Type"
@@ -32,6 +39,7 @@ const (
Type_Options_field_name protoreflect.Name = "options" Type_Options_field_name protoreflect.Name = "options"
Type_SourceContext_field_name protoreflect.Name = "source_context" Type_SourceContext_field_name protoreflect.Name = "source_context"
Type_Syntax_field_name protoreflect.Name = "syntax" Type_Syntax_field_name protoreflect.Name = "syntax"
Type_Edition_field_name protoreflect.Name = "edition"
Type_Name_field_fullname protoreflect.FullName = "google.protobuf.Type.name" Type_Name_field_fullname protoreflect.FullName = "google.protobuf.Type.name"
Type_Fields_field_fullname protoreflect.FullName = "google.protobuf.Type.fields" Type_Fields_field_fullname protoreflect.FullName = "google.protobuf.Type.fields"
@@ -39,6 +47,7 @@ const (
Type_Options_field_fullname protoreflect.FullName = "google.protobuf.Type.options" Type_Options_field_fullname protoreflect.FullName = "google.protobuf.Type.options"
Type_SourceContext_field_fullname protoreflect.FullName = "google.protobuf.Type.source_context" Type_SourceContext_field_fullname protoreflect.FullName = "google.protobuf.Type.source_context"
Type_Syntax_field_fullname protoreflect.FullName = "google.protobuf.Type.syntax" Type_Syntax_field_fullname protoreflect.FullName = "google.protobuf.Type.syntax"
Type_Edition_field_fullname protoreflect.FullName = "google.protobuf.Type.edition"
) )
// Field numbers for google.protobuf.Type. // Field numbers for google.protobuf.Type.
@@ -49,6 +58,7 @@ const (
Type_Options_field_number protoreflect.FieldNumber = 4 Type_Options_field_number protoreflect.FieldNumber = 4
Type_SourceContext_field_number protoreflect.FieldNumber = 5 Type_SourceContext_field_number protoreflect.FieldNumber = 5
Type_Syntax_field_number protoreflect.FieldNumber = 6 Type_Syntax_field_number protoreflect.FieldNumber = 6
Type_Edition_field_number protoreflect.FieldNumber = 7
) )
// Names for google.protobuf.Field. // Names for google.protobuf.Field.
@@ -102,12 +112,43 @@ const (
Field_Kind_enum_name = "Kind" Field_Kind_enum_name = "Kind"
) )
// Enum values for google.protobuf.Field.Kind.
const (
Field_TYPE_UNKNOWN_enum_value = 0
Field_TYPE_DOUBLE_enum_value = 1
Field_TYPE_FLOAT_enum_value = 2
Field_TYPE_INT64_enum_value = 3
Field_TYPE_UINT64_enum_value = 4
Field_TYPE_INT32_enum_value = 5
Field_TYPE_FIXED64_enum_value = 6
Field_TYPE_FIXED32_enum_value = 7
Field_TYPE_BOOL_enum_value = 8
Field_TYPE_STRING_enum_value = 9
Field_TYPE_GROUP_enum_value = 10
Field_TYPE_MESSAGE_enum_value = 11
Field_TYPE_BYTES_enum_value = 12
Field_TYPE_UINT32_enum_value = 13
Field_TYPE_ENUM_enum_value = 14
Field_TYPE_SFIXED32_enum_value = 15
Field_TYPE_SFIXED64_enum_value = 16
Field_TYPE_SINT32_enum_value = 17
Field_TYPE_SINT64_enum_value = 18
)
// Full and short names for google.protobuf.Field.Cardinality. // Full and short names for google.protobuf.Field.Cardinality.
const ( const (
Field_Cardinality_enum_fullname = "google.protobuf.Field.Cardinality" Field_Cardinality_enum_fullname = "google.protobuf.Field.Cardinality"
Field_Cardinality_enum_name = "Cardinality" Field_Cardinality_enum_name = "Cardinality"
) )
// Enum values for google.protobuf.Field.Cardinality.
const (
Field_CARDINALITY_UNKNOWN_enum_value = 0
Field_CARDINALITY_OPTIONAL_enum_value = 1
Field_CARDINALITY_REQUIRED_enum_value = 2
Field_CARDINALITY_REPEATED_enum_value = 3
)
// Names for google.protobuf.Enum. // Names for google.protobuf.Enum.
const ( const (
Enum_message_name protoreflect.Name = "Enum" Enum_message_name protoreflect.Name = "Enum"
@@ -121,12 +162,14 @@ const (
Enum_Options_field_name protoreflect.Name = "options" Enum_Options_field_name protoreflect.Name = "options"
Enum_SourceContext_field_name protoreflect.Name = "source_context" Enum_SourceContext_field_name protoreflect.Name = "source_context"
Enum_Syntax_field_name protoreflect.Name = "syntax" Enum_Syntax_field_name protoreflect.Name = "syntax"
Enum_Edition_field_name protoreflect.Name = "edition"
Enum_Name_field_fullname protoreflect.FullName = "google.protobuf.Enum.name" Enum_Name_field_fullname protoreflect.FullName = "google.protobuf.Enum.name"
Enum_Enumvalue_field_fullname protoreflect.FullName = "google.protobuf.Enum.enumvalue" Enum_Enumvalue_field_fullname protoreflect.FullName = "google.protobuf.Enum.enumvalue"
Enum_Options_field_fullname protoreflect.FullName = "google.protobuf.Enum.options" Enum_Options_field_fullname protoreflect.FullName = "google.protobuf.Enum.options"
Enum_SourceContext_field_fullname protoreflect.FullName = "google.protobuf.Enum.source_context" Enum_SourceContext_field_fullname protoreflect.FullName = "google.protobuf.Enum.source_context"
Enum_Syntax_field_fullname protoreflect.FullName = "google.protobuf.Enum.syntax" Enum_Syntax_field_fullname protoreflect.FullName = "google.protobuf.Enum.syntax"
Enum_Edition_field_fullname protoreflect.FullName = "google.protobuf.Enum.edition"
) )
// Field numbers for google.protobuf.Enum. // Field numbers for google.protobuf.Enum.
@@ -136,6 +179,7 @@ const (
Enum_Options_field_number protoreflect.FieldNumber = 3 Enum_Options_field_number protoreflect.FieldNumber = 3
Enum_SourceContext_field_number protoreflect.FieldNumber = 4 Enum_SourceContext_field_number protoreflect.FieldNumber = 4
Enum_Syntax_field_number protoreflect.FieldNumber = 5 Enum_Syntax_field_number protoreflect.FieldNumber = 5
Enum_Edition_field_number protoreflect.FieldNumber = 6
) )
// Names for google.protobuf.EnumValue. // Names for google.protobuf.EnumValue.

View File

@@ -12,8 +12,8 @@ import (
"google.golang.org/protobuf/encoding/prototext" "google.golang.org/protobuf/encoding/prototext"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
// Export is a zero-length named type that exists only to export a set of // Export is a zero-length named type that exists only to export a set of
@@ -32,11 +32,11 @@ type enum = interface{}
// EnumOf returns the protoreflect.Enum interface over e. // EnumOf returns the protoreflect.Enum interface over e.
// It returns nil if e is nil. // It returns nil if e is nil.
func (Export) EnumOf(e enum) pref.Enum { func (Export) EnumOf(e enum) protoreflect.Enum {
switch e := e.(type) { switch e := e.(type) {
case nil: case nil:
return nil return nil
case pref.Enum: case protoreflect.Enum:
return e return e
default: default:
return legacyWrapEnum(reflect.ValueOf(e)) return legacyWrapEnum(reflect.ValueOf(e))
@@ -45,11 +45,11 @@ func (Export) EnumOf(e enum) pref.Enum {
// EnumDescriptorOf returns the protoreflect.EnumDescriptor for e. // EnumDescriptorOf returns the protoreflect.EnumDescriptor for e.
// It returns nil if e is nil. // It returns nil if e is nil.
func (Export) EnumDescriptorOf(e enum) pref.EnumDescriptor { func (Export) EnumDescriptorOf(e enum) protoreflect.EnumDescriptor {
switch e := e.(type) { switch e := e.(type) {
case nil: case nil:
return nil return nil
case pref.Enum: case protoreflect.Enum:
return e.Descriptor() return e.Descriptor()
default: default:
return LegacyLoadEnumDesc(reflect.TypeOf(e)) return LegacyLoadEnumDesc(reflect.TypeOf(e))
@@ -58,11 +58,11 @@ func (Export) EnumDescriptorOf(e enum) pref.EnumDescriptor {
// EnumTypeOf returns the protoreflect.EnumType for e. // EnumTypeOf returns the protoreflect.EnumType for e.
// It returns nil if e is nil. // It returns nil if e is nil.
func (Export) EnumTypeOf(e enum) pref.EnumType { func (Export) EnumTypeOf(e enum) protoreflect.EnumType {
switch e := e.(type) { switch e := e.(type) {
case nil: case nil:
return nil return nil
case pref.Enum: case protoreflect.Enum:
return e.Type() return e.Type()
default: default:
return legacyLoadEnumType(reflect.TypeOf(e)) return legacyLoadEnumType(reflect.TypeOf(e))
@@ -71,7 +71,7 @@ func (Export) EnumTypeOf(e enum) pref.EnumType {
// EnumStringOf returns the enum value as a string, either as the name if // EnumStringOf returns the enum value as a string, either as the name if
// the number is resolvable, or the number formatted as a string. // the number is resolvable, or the number formatted as a string.
func (Export) EnumStringOf(ed pref.EnumDescriptor, n pref.EnumNumber) string { func (Export) EnumStringOf(ed protoreflect.EnumDescriptor, n protoreflect.EnumNumber) string {
ev := ed.Values().ByNumber(n) ev := ed.Values().ByNumber(n)
if ev != nil { if ev != nil {
return string(ev.Name()) return string(ev.Name())
@@ -84,7 +84,7 @@ func (Export) EnumStringOf(ed pref.EnumDescriptor, n pref.EnumNumber) string {
type message = interface{} type message = interface{}
// legacyMessageWrapper wraps a v2 message as a v1 message. // legacyMessageWrapper wraps a v2 message as a v1 message.
type legacyMessageWrapper struct{ m pref.ProtoMessage } type legacyMessageWrapper struct{ m protoreflect.ProtoMessage }
func (m legacyMessageWrapper) Reset() { proto.Reset(m.m) } func (m legacyMessageWrapper) Reset() { proto.Reset(m.m) }
func (m legacyMessageWrapper) String() string { return Export{}.MessageStringOf(m.m) } func (m legacyMessageWrapper) String() string { return Export{}.MessageStringOf(m.m) }
@@ -92,30 +92,30 @@ func (m legacyMessageWrapper) ProtoMessage() {}
// ProtoMessageV1Of converts either a v1 or v2 message to a v1 message. // ProtoMessageV1Of converts either a v1 or v2 message to a v1 message.
// It returns nil if m is nil. // It returns nil if m is nil.
func (Export) ProtoMessageV1Of(m message) piface.MessageV1 { func (Export) ProtoMessageV1Of(m message) protoiface.MessageV1 {
switch mv := m.(type) { switch mv := m.(type) {
case nil: case nil:
return nil return nil
case piface.MessageV1: case protoiface.MessageV1:
return mv return mv
case unwrapper: case unwrapper:
return Export{}.ProtoMessageV1Of(mv.protoUnwrap()) return Export{}.ProtoMessageV1Of(mv.protoUnwrap())
case pref.ProtoMessage: case protoreflect.ProtoMessage:
return legacyMessageWrapper{mv} return legacyMessageWrapper{mv}
default: default:
panic(fmt.Sprintf("message %T is neither a v1 or v2 Message", m)) panic(fmt.Sprintf("message %T is neither a v1 or v2 Message", m))
} }
} }
func (Export) protoMessageV2Of(m message) pref.ProtoMessage { func (Export) protoMessageV2Of(m message) protoreflect.ProtoMessage {
switch mv := m.(type) { switch mv := m.(type) {
case nil: case nil:
return nil return nil
case pref.ProtoMessage: case protoreflect.ProtoMessage:
return mv return mv
case legacyMessageWrapper: case legacyMessageWrapper:
return mv.m return mv.m
case piface.MessageV1: case protoiface.MessageV1:
return nil return nil
default: default:
panic(fmt.Sprintf("message %T is neither a v1 or v2 Message", m)) panic(fmt.Sprintf("message %T is neither a v1 or v2 Message", m))
@@ -124,7 +124,7 @@ func (Export) protoMessageV2Of(m message) pref.ProtoMessage {
// ProtoMessageV2Of converts either a v1 or v2 message to a v2 message. // ProtoMessageV2Of converts either a v1 or v2 message to a v2 message.
// It returns nil if m is nil. // It returns nil if m is nil.
func (Export) ProtoMessageV2Of(m message) pref.ProtoMessage { func (Export) ProtoMessageV2Of(m message) protoreflect.ProtoMessage {
if m == nil { if m == nil {
return nil return nil
} }
@@ -136,7 +136,7 @@ func (Export) ProtoMessageV2Of(m message) pref.ProtoMessage {
// MessageOf returns the protoreflect.Message interface over m. // MessageOf returns the protoreflect.Message interface over m.
// It returns nil if m is nil. // It returns nil if m is nil.
func (Export) MessageOf(m message) pref.Message { func (Export) MessageOf(m message) protoreflect.Message {
if m == nil { if m == nil {
return nil return nil
} }
@@ -148,7 +148,7 @@ func (Export) MessageOf(m message) pref.Message {
// MessageDescriptorOf returns the protoreflect.MessageDescriptor for m. // MessageDescriptorOf returns the protoreflect.MessageDescriptor for m.
// It returns nil if m is nil. // It returns nil if m is nil.
func (Export) MessageDescriptorOf(m message) pref.MessageDescriptor { func (Export) MessageDescriptorOf(m message) protoreflect.MessageDescriptor {
if m == nil { if m == nil {
return nil return nil
} }
@@ -160,7 +160,7 @@ func (Export) MessageDescriptorOf(m message) pref.MessageDescriptor {
// MessageTypeOf returns the protoreflect.MessageType for m. // MessageTypeOf returns the protoreflect.MessageType for m.
// It returns nil if m is nil. // It returns nil if m is nil.
func (Export) MessageTypeOf(m message) pref.MessageType { func (Export) MessageTypeOf(m message) protoreflect.MessageType {
if m == nil { if m == nil {
return nil return nil
} }
@@ -172,6 +172,6 @@ func (Export) MessageTypeOf(m message) pref.MessageType {
// MessageStringOf returns the message value as a string, // MessageStringOf returns the message value as a string,
// which is the message serialized in the protobuf text format. // which is the message serialized in the protobuf text format.
func (Export) MessageStringOf(m pref.ProtoMessage) string { func (Export) MessageStringOf(m protoreflect.ProtoMessage) string {
return prototext.MarshalOptions{Multiline: false}.Format(m) return prototext.MarshalOptions{Multiline: false}.Format(m)
} }

View File

@@ -8,18 +8,18 @@ import (
"sync" "sync"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
func (mi *MessageInfo) checkInitialized(in piface.CheckInitializedInput) (piface.CheckInitializedOutput, error) { func (mi *MessageInfo) checkInitialized(in protoiface.CheckInitializedInput) (protoiface.CheckInitializedOutput, error) {
var p pointer var p pointer
if ms, ok := in.Message.(*messageState); ok { if ms, ok := in.Message.(*messageState); ok {
p = ms.pointer() p = ms.pointer()
} else { } else {
p = in.Message.(*messageReflectWrapper).pointer() p = in.Message.(*messageReflectWrapper).pointer()
} }
return piface.CheckInitializedOutput{}, mi.checkInitializedPointer(p) return protoiface.CheckInitializedOutput{}, mi.checkInitializedPointer(p)
} }
func (mi *MessageInfo) checkInitializedPointer(p pointer) error { func (mi *MessageInfo) checkInitializedPointer(p pointer) error {
@@ -90,7 +90,7 @@ var (
// needsInitCheck reports whether a message needs to be checked for partial initialization. // needsInitCheck reports whether a message needs to be checked for partial initialization.
// //
// It returns true if the message transitively includes any required or extension fields. // It returns true if the message transitively includes any required or extension fields.
func needsInitCheck(md pref.MessageDescriptor) bool { func needsInitCheck(md protoreflect.MessageDescriptor) bool {
if v, ok := needsInitCheckMap.Load(md); ok { if v, ok := needsInitCheckMap.Load(md); ok {
if has, ok := v.(bool); ok { if has, ok := v.(bool); ok {
return has return has
@@ -101,7 +101,7 @@ func needsInitCheck(md pref.MessageDescriptor) bool {
return needsInitCheckLocked(md) return needsInitCheckLocked(md)
} }
func needsInitCheckLocked(md pref.MessageDescriptor) (has bool) { func needsInitCheckLocked(md protoreflect.MessageDescriptor) (has bool) {
if v, ok := needsInitCheckMap.Load(md); ok { if v, ok := needsInitCheckMap.Load(md); ok {
// If has is true, we've previously determined that this message // If has is true, we've previously determined that this message
// needs init checks. // needs init checks.

View File

@@ -10,7 +10,7 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
type extensionFieldInfo struct { type extensionFieldInfo struct {
@@ -21,29 +21,21 @@ type extensionFieldInfo struct {
validation validationInfo validation validationInfo
} }
var legacyExtensionFieldInfoCache sync.Map // map[protoreflect.ExtensionType]*extensionFieldInfo func getExtensionFieldInfo(xt protoreflect.ExtensionType) *extensionFieldInfo {
func getExtensionFieldInfo(xt pref.ExtensionType) *extensionFieldInfo {
if xi, ok := xt.(*ExtensionInfo); ok { if xi, ok := xt.(*ExtensionInfo); ok {
xi.lazyInit() xi.lazyInit()
return xi.info return xi.info
} }
return legacyLoadExtensionFieldInfo(xt) // Ideally we'd cache the resulting *extensionFieldInfo so we don't have to
// recompute this metadata repeatedly. But without support for something like
// weak references, such a cache would pin temporary values (like dynamic
// extension types, constructed for the duration of a user request) to the
// heap forever, causing memory usage of the cache to grow unbounded.
// See discussion in https://github.com/golang/protobuf/issues/1521.
return makeExtensionFieldInfo(xt.TypeDescriptor())
} }
// legacyLoadExtensionFieldInfo dynamically loads a *ExtensionInfo for xt. func makeExtensionFieldInfo(xd protoreflect.ExtensionDescriptor) *extensionFieldInfo {
func legacyLoadExtensionFieldInfo(xt pref.ExtensionType) *extensionFieldInfo {
if xi, ok := legacyExtensionFieldInfoCache.Load(xt); ok {
return xi.(*extensionFieldInfo)
}
e := makeExtensionFieldInfo(xt.TypeDescriptor())
if e, ok := legacyMessageTypeCache.LoadOrStore(xt, e); ok {
return e.(*extensionFieldInfo)
}
return e
}
func makeExtensionFieldInfo(xd pref.ExtensionDescriptor) *extensionFieldInfo {
var wiretag uint64 var wiretag uint64
if !xd.IsPacked() { if !xd.IsPacked() {
wiretag = protowire.EncodeTag(xd.Number(), wireTypes[xd.Kind()]) wiretag = protowire.EncodeTag(xd.Number(), wireTypes[xd.Kind()])
@@ -59,10 +51,10 @@ func makeExtensionFieldInfo(xd pref.ExtensionDescriptor) *extensionFieldInfo {
// This is true for composite types, where we pass in a message, list, or map to fill in, // This is true for composite types, where we pass in a message, list, or map to fill in,
// and for enums, where we pass in a prototype value to specify the concrete enum type. // and for enums, where we pass in a prototype value to specify the concrete enum type.
switch xd.Kind() { switch xd.Kind() {
case pref.MessageKind, pref.GroupKind, pref.EnumKind: case protoreflect.MessageKind, protoreflect.GroupKind, protoreflect.EnumKind:
e.unmarshalNeedsValue = true e.unmarshalNeedsValue = true
default: default:
if xd.Cardinality() == pref.Repeated { if xd.Cardinality() == protoreflect.Repeated {
e.unmarshalNeedsValue = true e.unmarshalNeedsValue = true
} }
} }
@@ -73,21 +65,21 @@ type lazyExtensionValue struct {
atomicOnce uint32 // atomically set if value is valid atomicOnce uint32 // atomically set if value is valid
mu sync.Mutex mu sync.Mutex
xi *extensionFieldInfo xi *extensionFieldInfo
value pref.Value value protoreflect.Value
b []byte b []byte
fn func() pref.Value fn func() protoreflect.Value
} }
type ExtensionField struct { type ExtensionField struct {
typ pref.ExtensionType typ protoreflect.ExtensionType
// value is either the value of GetValue, // value is either the value of GetValue,
// or a *lazyExtensionValue that then returns the value of GetValue. // or a *lazyExtensionValue that then returns the value of GetValue.
value pref.Value value protoreflect.Value
lazy *lazyExtensionValue lazy *lazyExtensionValue
} }
func (f *ExtensionField) appendLazyBytes(xt pref.ExtensionType, xi *extensionFieldInfo, num protowire.Number, wtyp protowire.Type, b []byte) { func (f *ExtensionField) appendLazyBytes(xt protoreflect.ExtensionType, xi *extensionFieldInfo, num protowire.Number, wtyp protowire.Type, b []byte) {
if f.lazy == nil { if f.lazy == nil {
f.lazy = &lazyExtensionValue{xi: xi} f.lazy = &lazyExtensionValue{xi: xi}
} }
@@ -97,7 +89,7 @@ func (f *ExtensionField) appendLazyBytes(xt pref.ExtensionType, xi *extensionFie
f.lazy.b = append(f.lazy.b, b...) f.lazy.b = append(f.lazy.b, b...)
} }
func (f *ExtensionField) canLazy(xt pref.ExtensionType) bool { func (f *ExtensionField) canLazy(xt protoreflect.ExtensionType) bool {
if f.typ == nil { if f.typ == nil {
return true return true
} }
@@ -154,7 +146,7 @@ func (f *ExtensionField) lazyInit() {
// Set sets the type and value of the extension field. // Set sets the type and value of the extension field.
// This must not be called concurrently. // This must not be called concurrently.
func (f *ExtensionField) Set(t pref.ExtensionType, v pref.Value) { func (f *ExtensionField) Set(t protoreflect.ExtensionType, v protoreflect.Value) {
f.typ = t f.typ = t
f.value = v f.value = v
f.lazy = nil f.lazy = nil
@@ -162,14 +154,14 @@ func (f *ExtensionField) Set(t pref.ExtensionType, v pref.Value) {
// SetLazy sets the type and a value that is to be lazily evaluated upon first use. // SetLazy sets the type and a value that is to be lazily evaluated upon first use.
// This must not be called concurrently. // This must not be called concurrently.
func (f *ExtensionField) SetLazy(t pref.ExtensionType, fn func() pref.Value) { func (f *ExtensionField) SetLazy(t protoreflect.ExtensionType, fn func() protoreflect.Value) {
f.typ = t f.typ = t
f.lazy = &lazyExtensionValue{fn: fn} f.lazy = &lazyExtensionValue{fn: fn}
} }
// Value returns the value of the extension field. // Value returns the value of the extension field.
// This may be called concurrently. // This may be called concurrently.
func (f *ExtensionField) Value() pref.Value { func (f *ExtensionField) Value() protoreflect.Value {
if f.lazy != nil { if f.lazy != nil {
if atomic.LoadUint32(&f.lazy.atomicOnce) == 0 { if atomic.LoadUint32(&f.lazy.atomicOnce) == 0 {
f.lazyInit() f.lazyInit()
@@ -181,7 +173,7 @@ func (f *ExtensionField) Value() pref.Value {
// Type returns the type of the extension field. // Type returns the type of the extension field.
// This may be called concurrently. // This may be called concurrently.
func (f ExtensionField) Type() pref.ExtensionType { func (f ExtensionField) Type() protoreflect.ExtensionType {
return f.typ return f.typ
} }
@@ -193,7 +185,7 @@ func (f ExtensionField) IsSet() bool {
// IsLazy reports whether a field is lazily encoded. // IsLazy reports whether a field is lazily encoded.
// It is exported for testing. // It is exported for testing.
func IsLazy(m pref.Message, fd pref.FieldDescriptor) bool { func IsLazy(m protoreflect.Message, fd protoreflect.FieldDescriptor) bool {
var mi *MessageInfo var mi *MessageInfo
var p pointer var p pointer
switch m := m.(type) { switch m := m.(type) {
@@ -206,7 +198,7 @@ func IsLazy(m pref.Message, fd pref.FieldDescriptor) bool {
default: default:
return false return false
} }
xd, ok := fd.(pref.ExtensionTypeDescriptor) xd, ok := fd.(protoreflect.ExtensionTypeDescriptor)
if !ok { if !ok {
return false return false
} }

View File

@@ -12,9 +12,9 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
preg "google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
type errInvalidUTF8 struct{} type errInvalidUTF8 struct{}
@@ -30,7 +30,7 @@ func (errInvalidUTF8) Unwrap() error { return errors.Error }
// to the appropriate field-specific function as necessary. // to the appropriate field-specific function as necessary.
// //
// The unmarshal function is set on each field individually as usual. // The unmarshal function is set on each field individually as usual.
func (mi *MessageInfo) initOneofFieldCoders(od pref.OneofDescriptor, si structInfo) { func (mi *MessageInfo) initOneofFieldCoders(od protoreflect.OneofDescriptor, si structInfo) {
fs := si.oneofsByName[od.Name()] fs := si.oneofsByName[od.Name()]
ft := fs.Type ft := fs.Type
oneofFields := make(map[reflect.Type]*coderFieldInfo) oneofFields := make(map[reflect.Type]*coderFieldInfo)
@@ -118,13 +118,13 @@ func (mi *MessageInfo) initOneofFieldCoders(od pref.OneofDescriptor, si structIn
} }
} }
func makeWeakMessageFieldCoder(fd pref.FieldDescriptor) pointerCoderFuncs { func makeWeakMessageFieldCoder(fd protoreflect.FieldDescriptor) pointerCoderFuncs {
var once sync.Once var once sync.Once
var messageType pref.MessageType var messageType protoreflect.MessageType
lazyInit := func() { lazyInit := func() {
once.Do(func() { once.Do(func() {
messageName := fd.Message().FullName() messageName := fd.Message().FullName()
messageType, _ = preg.GlobalTypes.FindMessageByName(messageName) messageType, _ = protoregistry.GlobalTypes.FindMessageByName(messageName)
}) })
} }
@@ -190,7 +190,7 @@ func makeWeakMessageFieldCoder(fd pref.FieldDescriptor) pointerCoderFuncs {
} }
} }
func makeMessageFieldCoder(fd pref.FieldDescriptor, ft reflect.Type) pointerCoderFuncs { func makeMessageFieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) pointerCoderFuncs {
if mi := getMessageInfo(ft); mi != nil { if mi := getMessageInfo(ft); mi != nil {
funcs := pointerCoderFuncs{ funcs := pointerCoderFuncs{
size: sizeMessageInfo, size: sizeMessageInfo,
@@ -280,7 +280,7 @@ func consumeMessage(b []byte, m proto.Message, wtyp protowire.Type, opts unmarsh
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: v, Buf: v,
Message: m.ProtoReflect(), Message: m.ProtoReflect(),
}) })
@@ -288,27 +288,27 @@ func consumeMessage(b []byte, m proto.Message, wtyp protowire.Type, opts unmarsh
return out, err return out, err
} }
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return out, nil return out, nil
} }
func sizeMessageValue(v pref.Value, tagsize int, opts marshalOptions) int { func sizeMessageValue(v protoreflect.Value, tagsize int, opts marshalOptions) int {
m := v.Message().Interface() m := v.Message().Interface()
return sizeMessage(m, tagsize, opts) return sizeMessage(m, tagsize, opts)
} }
func appendMessageValue(b []byte, v pref.Value, wiretag uint64, opts marshalOptions) ([]byte, error) { func appendMessageValue(b []byte, v protoreflect.Value, wiretag uint64, opts marshalOptions) ([]byte, error) {
m := v.Message().Interface() m := v.Message().Interface()
return appendMessage(b, m, wiretag, opts) return appendMessage(b, m, wiretag, opts)
} }
func consumeMessageValue(b []byte, v pref.Value, _ protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (pref.Value, unmarshalOutput, error) { func consumeMessageValue(b []byte, v protoreflect.Value, _ protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (protoreflect.Value, unmarshalOutput, error) {
m := v.Message().Interface() m := v.Message().Interface()
out, err := consumeMessage(b, m, wtyp, opts) out, err := consumeMessage(b, m, wtyp, opts)
return v, out, err return v, out, err
} }
func isInitMessageValue(v pref.Value) error { func isInitMessageValue(v protoreflect.Value) error {
m := v.Message().Interface() m := v.Message().Interface()
return proto.CheckInitialized(m) return proto.CheckInitialized(m)
} }
@@ -321,17 +321,17 @@ var coderMessageValue = valueCoderFuncs{
merge: mergeMessageValue, merge: mergeMessageValue,
} }
func sizeGroupValue(v pref.Value, tagsize int, opts marshalOptions) int { func sizeGroupValue(v protoreflect.Value, tagsize int, opts marshalOptions) int {
m := v.Message().Interface() m := v.Message().Interface()
return sizeGroup(m, tagsize, opts) return sizeGroup(m, tagsize, opts)
} }
func appendGroupValue(b []byte, v pref.Value, wiretag uint64, opts marshalOptions) ([]byte, error) { func appendGroupValue(b []byte, v protoreflect.Value, wiretag uint64, opts marshalOptions) ([]byte, error) {
m := v.Message().Interface() m := v.Message().Interface()
return appendGroup(b, m, wiretag, opts) return appendGroup(b, m, wiretag, opts)
} }
func consumeGroupValue(b []byte, v pref.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (pref.Value, unmarshalOutput, error) { func consumeGroupValue(b []byte, v protoreflect.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (protoreflect.Value, unmarshalOutput, error) {
m := v.Message().Interface() m := v.Message().Interface()
out, err := consumeGroup(b, m, num, wtyp, opts) out, err := consumeGroup(b, m, num, wtyp, opts)
return v, out, err return v, out, err
@@ -345,7 +345,7 @@ var coderGroupValue = valueCoderFuncs{
merge: mergeMessageValue, merge: mergeMessageValue,
} }
func makeGroupFieldCoder(fd pref.FieldDescriptor, ft reflect.Type) pointerCoderFuncs { func makeGroupFieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) pointerCoderFuncs {
num := fd.Number() num := fd.Number()
if mi := getMessageInfo(ft); mi != nil { if mi := getMessageInfo(ft); mi != nil {
funcs := pointerCoderFuncs{ funcs := pointerCoderFuncs{
@@ -424,7 +424,7 @@ func consumeGroup(b []byte, m proto.Message, num protowire.Number, wtyp protowir
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: b, Buf: b,
Message: m.ProtoReflect(), Message: m.ProtoReflect(),
}) })
@@ -432,11 +432,11 @@ func consumeGroup(b []byte, m proto.Message, num protowire.Number, wtyp protowir
return out, err return out, err
} }
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return out, nil return out, nil
} }
func makeMessageSliceFieldCoder(fd pref.FieldDescriptor, ft reflect.Type) pointerCoderFuncs { func makeMessageSliceFieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) pointerCoderFuncs {
if mi := getMessageInfo(ft); mi != nil { if mi := getMessageInfo(ft); mi != nil {
funcs := pointerCoderFuncs{ funcs := pointerCoderFuncs{
size: sizeMessageSliceInfo, size: sizeMessageSliceInfo,
@@ -555,7 +555,7 @@ func consumeMessageSlice(b []byte, p pointer, goType reflect.Type, wtyp protowir
return out, errDecode return out, errDecode
} }
mp := reflect.New(goType.Elem()) mp := reflect.New(goType.Elem())
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: v, Buf: v,
Message: asMessage(mp).ProtoReflect(), Message: asMessage(mp).ProtoReflect(),
}) })
@@ -564,7 +564,7 @@ func consumeMessageSlice(b []byte, p pointer, goType reflect.Type, wtyp protowir
} }
p.AppendPointerSlice(pointerOfValue(mp)) p.AppendPointerSlice(pointerOfValue(mp))
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return out, nil return out, nil
} }
@@ -581,7 +581,7 @@ func isInitMessageSlice(p pointer, goType reflect.Type) error {
// Slices of messages // Slices of messages
func sizeMessageSliceValue(listv pref.Value, tagsize int, opts marshalOptions) int { func sizeMessageSliceValue(listv protoreflect.Value, tagsize int, opts marshalOptions) int {
list := listv.List() list := listv.List()
n := 0 n := 0
for i, llen := 0, list.Len(); i < llen; i++ { for i, llen := 0, list.Len(); i < llen; i++ {
@@ -591,7 +591,7 @@ func sizeMessageSliceValue(listv pref.Value, tagsize int, opts marshalOptions) i
return n return n
} }
func appendMessageSliceValue(b []byte, listv pref.Value, wiretag uint64, opts marshalOptions) ([]byte, error) { func appendMessageSliceValue(b []byte, listv protoreflect.Value, wiretag uint64, opts marshalOptions) ([]byte, error) {
list := listv.List() list := listv.List()
mopts := opts.Options() mopts := opts.Options()
for i, llen := 0, list.Len(); i < llen; i++ { for i, llen := 0, list.Len(); i < llen; i++ {
@@ -608,30 +608,30 @@ func appendMessageSliceValue(b []byte, listv pref.Value, wiretag uint64, opts ma
return b, nil return b, nil
} }
func consumeMessageSliceValue(b []byte, listv pref.Value, _ protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (_ pref.Value, out unmarshalOutput, err error) { func consumeMessageSliceValue(b []byte, listv protoreflect.Value, _ protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (_ protoreflect.Value, out unmarshalOutput, err error) {
list := listv.List() list := listv.List()
if wtyp != protowire.BytesType { if wtyp != protowire.BytesType {
return pref.Value{}, out, errUnknown return protoreflect.Value{}, out, errUnknown
} }
v, n := protowire.ConsumeBytes(b) v, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return pref.Value{}, out, errDecode return protoreflect.Value{}, out, errDecode
} }
m := list.NewElement() m := list.NewElement()
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: v, Buf: v,
Message: m.Message(), Message: m.Message(),
}) })
if err != nil { if err != nil {
return pref.Value{}, out, err return protoreflect.Value{}, out, err
} }
list.Append(m) list.Append(m)
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return listv, out, nil return listv, out, nil
} }
func isInitMessageSliceValue(listv pref.Value) error { func isInitMessageSliceValue(listv protoreflect.Value) error {
list := listv.List() list := listv.List()
for i, llen := 0, list.Len(); i < llen; i++ { for i, llen := 0, list.Len(); i < llen; i++ {
m := list.Get(i).Message().Interface() m := list.Get(i).Message().Interface()
@@ -650,7 +650,7 @@ var coderMessageSliceValue = valueCoderFuncs{
merge: mergeMessageListValue, merge: mergeMessageListValue,
} }
func sizeGroupSliceValue(listv pref.Value, tagsize int, opts marshalOptions) int { func sizeGroupSliceValue(listv protoreflect.Value, tagsize int, opts marshalOptions) int {
list := listv.List() list := listv.List()
n := 0 n := 0
for i, llen := 0, list.Len(); i < llen; i++ { for i, llen := 0, list.Len(); i < llen; i++ {
@@ -660,7 +660,7 @@ func sizeGroupSliceValue(listv pref.Value, tagsize int, opts marshalOptions) int
return n return n
} }
func appendGroupSliceValue(b []byte, listv pref.Value, wiretag uint64, opts marshalOptions) ([]byte, error) { func appendGroupSliceValue(b []byte, listv protoreflect.Value, wiretag uint64, opts marshalOptions) ([]byte, error) {
list := listv.List() list := listv.List()
mopts := opts.Options() mopts := opts.Options()
for i, llen := 0, list.Len(); i < llen; i++ { for i, llen := 0, list.Len(); i < llen; i++ {
@@ -676,26 +676,26 @@ func appendGroupSliceValue(b []byte, listv pref.Value, wiretag uint64, opts mars
return b, nil return b, nil
} }
func consumeGroupSliceValue(b []byte, listv pref.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (_ pref.Value, out unmarshalOutput, err error) { func consumeGroupSliceValue(b []byte, listv protoreflect.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (_ protoreflect.Value, out unmarshalOutput, err error) {
list := listv.List() list := listv.List()
if wtyp != protowire.StartGroupType { if wtyp != protowire.StartGroupType {
return pref.Value{}, out, errUnknown return protoreflect.Value{}, out, errUnknown
} }
b, n := protowire.ConsumeGroup(num, b) b, n := protowire.ConsumeGroup(num, b)
if n < 0 { if n < 0 {
return pref.Value{}, out, errDecode return protoreflect.Value{}, out, errDecode
} }
m := list.NewElement() m := list.NewElement()
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: b, Buf: b,
Message: m.Message(), Message: m.Message(),
}) })
if err != nil { if err != nil {
return pref.Value{}, out, err return protoreflect.Value{}, out, err
} }
list.Append(m) list.Append(m)
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return listv, out, nil return listv, out, nil
} }
@@ -707,7 +707,7 @@ var coderGroupSliceValue = valueCoderFuncs{
merge: mergeMessageListValue, merge: mergeMessageListValue,
} }
func makeGroupSliceFieldCoder(fd pref.FieldDescriptor, ft reflect.Type) pointerCoderFuncs { func makeGroupSliceFieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) pointerCoderFuncs {
num := fd.Number() num := fd.Number()
if mi := getMessageInfo(ft); mi != nil { if mi := getMessageInfo(ft); mi != nil {
funcs := pointerCoderFuncs{ funcs := pointerCoderFuncs{
@@ -772,7 +772,7 @@ func consumeGroupSlice(b []byte, p pointer, num protowire.Number, wtyp protowire
return out, errDecode return out, errDecode
} }
mp := reflect.New(goType.Elem()) mp := reflect.New(goType.Elem())
o, err := opts.Options().UnmarshalState(piface.UnmarshalInput{ o, err := opts.Options().UnmarshalState(protoiface.UnmarshalInput{
Buf: b, Buf: b,
Message: asMessage(mp).ProtoReflect(), Message: asMessage(mp).ProtoReflect(),
}) })
@@ -781,7 +781,7 @@ func consumeGroupSlice(b []byte, p pointer, num protowire.Number, wtyp protowire
} }
p.AppendPointerSlice(pointerOfValue(mp)) p.AppendPointerSlice(pointerOfValue(mp))
out.n = n out.n = n
out.initialized = o.Flags&piface.UnmarshalInitialized != 0 out.initialized = o.Flags&protoiface.UnmarshalInitialized != 0
return out, nil return out, nil
} }
@@ -822,8 +822,8 @@ func consumeGroupSliceInfo(b []byte, p pointer, wtyp protowire.Type, f *coderFie
return out, nil return out, nil
} }
func asMessage(v reflect.Value) pref.ProtoMessage { func asMessage(v reflect.Value) protoreflect.ProtoMessage {
if m, ok := v.Interface().(pref.ProtoMessage); ok { if m, ok := v.Interface().(protoreflect.ProtoMessage); ok {
return m return m
} }
return legacyWrapMessage(v).Interface() return legacyWrapMessage(v).Interface()

View File

@@ -162,11 +162,20 @@ func appendBoolSlice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptions
func consumeBoolSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeBoolSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.BoolSlice() sp := p.BoolSlice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growBoolSlice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -732,11 +741,20 @@ func appendInt32Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOption
func consumeInt32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeInt32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int32Slice() sp := p.Int32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growInt32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -1138,11 +1156,20 @@ func appendSint32Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptio
func consumeSint32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeSint32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int32Slice() sp := p.Int32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growInt32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -1544,11 +1571,20 @@ func appendUint32Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptio
func consumeUint32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeUint32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Uint32Slice() sp := p.Uint32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growUint32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -1950,11 +1986,20 @@ func appendInt64Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOption
func consumeInt64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeInt64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int64Slice() sp := p.Int64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growInt64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -2356,11 +2401,20 @@ func appendSint64Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptio
func consumeSint64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeSint64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int64Slice() sp := p.Int64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growInt64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -2762,11 +2816,20 @@ func appendUint64Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptio
func consumeUint64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeUint64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Uint64Slice() sp := p.Uint64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := 0
for _, v := range b {
if v < 0x80 {
count++
}
}
if count > 0 {
p.growUint64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
var v uint64 var v uint64
var n int var n int
@@ -3145,11 +3208,15 @@ func appendSfixed32Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOpt
func consumeSfixed32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeSfixed32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int32Slice() sp := p.Int32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed32()
if count > 0 {
p.growInt32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed32(b) v, n := protowire.ConsumeFixed32(b)
if n < 0 { if n < 0 {
@@ -3461,11 +3528,15 @@ func appendFixed32Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOpti
func consumeFixed32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeFixed32Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Uint32Slice() sp := p.Uint32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed32()
if count > 0 {
p.growUint32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed32(b) v, n := protowire.ConsumeFixed32(b)
if n < 0 { if n < 0 {
@@ -3777,11 +3848,15 @@ func appendFloatSlice(b []byte, p pointer, f *coderFieldInfo, opts marshalOption
func consumeFloatSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeFloatSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Float32Slice() sp := p.Float32Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed32()
if count > 0 {
p.growFloat32Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed32(b) v, n := protowire.ConsumeFixed32(b)
if n < 0 { if n < 0 {
@@ -4093,11 +4168,15 @@ func appendSfixed64Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOpt
func consumeSfixed64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeSfixed64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Int64Slice() sp := p.Int64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed64()
if count > 0 {
p.growInt64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed64(b) v, n := protowire.ConsumeFixed64(b)
if n < 0 { if n < 0 {
@@ -4409,11 +4488,15 @@ func appendFixed64Slice(b []byte, p pointer, f *coderFieldInfo, opts marshalOpti
func consumeFixed64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeFixed64Slice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Uint64Slice() sp := p.Uint64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed64()
if count > 0 {
p.growUint64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed64(b) v, n := protowire.ConsumeFixed64(b)
if n < 0 { if n < 0 {
@@ -4725,11 +4808,15 @@ func appendDoubleSlice(b []byte, p pointer, f *coderFieldInfo, opts marshalOptio
func consumeDoubleSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) { func consumeDoubleSlice(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (out unmarshalOutput, err error) {
sp := p.Float64Slice() sp := p.Float64Slice()
if wtyp == protowire.BytesType { if wtyp == protowire.BytesType {
s := *sp
b, n := protowire.ConsumeBytes(b) b, n := protowire.ConsumeBytes(b)
if n < 0 { if n < 0 {
return out, errDecode return out, errDecode
} }
count := len(b) / protowire.SizeFixed64()
if count > 0 {
p.growFloat64Slice(count)
}
s := *sp
for len(b) > 0 { for len(b) > 0 {
v, n := protowire.ConsumeFixed64(b) v, n := protowire.ConsumeFixed64(b)
if n < 0 { if n < 0 {

View File

@@ -10,7 +10,7 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/genid"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
type mapInfo struct { type mapInfo struct {
@@ -19,12 +19,12 @@ type mapInfo struct {
valWiretag uint64 valWiretag uint64
keyFuncs valueCoderFuncs keyFuncs valueCoderFuncs
valFuncs valueCoderFuncs valFuncs valueCoderFuncs
keyZero pref.Value keyZero protoreflect.Value
keyKind pref.Kind keyKind protoreflect.Kind
conv *mapConverter conv *mapConverter
} }
func encoderFuncsForMap(fd pref.FieldDescriptor, ft reflect.Type) (valueMessage *MessageInfo, funcs pointerCoderFuncs) { func encoderFuncsForMap(fd protoreflect.FieldDescriptor, ft reflect.Type) (valueMessage *MessageInfo, funcs pointerCoderFuncs) {
// TODO: Consider generating specialized map coders. // TODO: Consider generating specialized map coders.
keyField := fd.MapKey() keyField := fd.MapKey()
valField := fd.MapValue() valField := fd.MapValue()
@@ -44,7 +44,7 @@ func encoderFuncsForMap(fd pref.FieldDescriptor, ft reflect.Type) (valueMessage
keyKind: keyField.Kind(), keyKind: keyField.Kind(),
conv: conv, conv: conv,
} }
if valField.Kind() == pref.MessageKind { if valField.Kind() == protoreflect.MessageKind {
valueMessage = getMessageInfo(ft.Elem()) valueMessage = getMessageInfo(ft.Elem())
} }
@@ -68,9 +68,9 @@ func encoderFuncsForMap(fd pref.FieldDescriptor, ft reflect.Type) (valueMessage
}, },
} }
switch valField.Kind() { switch valField.Kind() {
case pref.MessageKind: case protoreflect.MessageKind:
funcs.merge = mergeMapOfMessage funcs.merge = mergeMapOfMessage
case pref.BytesKind: case protoreflect.BytesKind:
funcs.merge = mergeMapOfBytes funcs.merge = mergeMapOfBytes
default: default:
funcs.merge = mergeMap funcs.merge = mergeMap
@@ -135,7 +135,7 @@ func consumeMap(b []byte, mapv reflect.Value, wtyp protowire.Type, mapi *mapInfo
err := errUnknown err := errUnknown
switch num { switch num {
case genid.MapEntry_Key_field_number: case genid.MapEntry_Key_field_number:
var v pref.Value var v protoreflect.Value
var o unmarshalOutput var o unmarshalOutput
v, o, err = mapi.keyFuncs.unmarshal(b, key, num, wtyp, opts) v, o, err = mapi.keyFuncs.unmarshal(b, key, num, wtyp, opts)
if err != nil { if err != nil {
@@ -144,7 +144,7 @@ func consumeMap(b []byte, mapv reflect.Value, wtyp protowire.Type, mapi *mapInfo
key = v key = v
n = o.n n = o.n
case genid.MapEntry_Value_field_number: case genid.MapEntry_Value_field_number:
var v pref.Value var v protoreflect.Value
var o unmarshalOutput var o unmarshalOutput
v, o, err = mapi.valFuncs.unmarshal(b, val, num, wtyp, opts) v, o, err = mapi.valFuncs.unmarshal(b, val, num, wtyp, opts)
if err != nil { if err != nil {
@@ -192,7 +192,7 @@ func consumeMapOfMessage(b []byte, mapv reflect.Value, wtyp protowire.Type, mapi
err := errUnknown err := errUnknown
switch num { switch num {
case 1: case 1:
var v pref.Value var v protoreflect.Value
var o unmarshalOutput var o unmarshalOutput
v, o, err = mapi.keyFuncs.unmarshal(b, key, num, wtyp, opts) v, o, err = mapi.keyFuncs.unmarshal(b, key, num, wtyp, opts)
if err != nil { if err != nil {

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build !go1.12
// +build !go1.12 // +build !go1.12
package impl package impl

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build go1.12
// +build go1.12 // +build go1.12
package impl package impl

View File

@@ -12,15 +12,15 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/encoding/messageset" "google.golang.org/protobuf/internal/encoding/messageset"
"google.golang.org/protobuf/internal/order" "google.golang.org/protobuf/internal/order"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
// coderMessageInfo contains per-message information used by the fast-path functions. // coderMessageInfo contains per-message information used by the fast-path functions.
// This is a different type from MessageInfo to keep MessageInfo as general-purpose as // This is a different type from MessageInfo to keep MessageInfo as general-purpose as
// possible. // possible.
type coderMessageInfo struct { type coderMessageInfo struct {
methods piface.Methods methods protoiface.Methods
orderedCoderFields []*coderFieldInfo orderedCoderFields []*coderFieldInfo
denseCoderFields []*coderFieldInfo denseCoderFields []*coderFieldInfo
@@ -39,7 +39,7 @@ type coderFieldInfo struct {
mi *MessageInfo // field's message mi *MessageInfo // field's message
ft reflect.Type ft reflect.Type
validation validationInfo // information used by message validation validation validationInfo // information used by message validation
num pref.FieldNumber // field number num protoreflect.FieldNumber // field number
offset offset // struct field offset offset offset // struct field offset
wiretag uint64 // field tag (number + wire type) wiretag uint64 // field tag (number + wire type)
tagsize int // size of the varint-encoded tag tagsize int // size of the varint-encoded tag
@@ -125,8 +125,8 @@ func (mi *MessageInfo) makeCoderMethods(t reflect.Type, si structInfo) {
funcs: funcs, funcs: funcs,
mi: childMessage, mi: childMessage,
validation: newFieldValidationInfo(mi, si, fd, ft), validation: newFieldValidationInfo(mi, si, fd, ft),
isPointer: fd.Cardinality() == pref.Repeated || fd.HasPresence(), isPointer: fd.Cardinality() == protoreflect.Repeated || fd.HasPresence(),
isRequired: fd.Cardinality() == pref.Required, isRequired: fd.Cardinality() == protoreflect.Required,
} }
mi.orderedCoderFields = append(mi.orderedCoderFields, cf) mi.orderedCoderFields = append(mi.orderedCoderFields, cf)
mi.coderFields[cf.num] = cf mi.coderFields[cf.num] = cf
@@ -149,7 +149,7 @@ func (mi *MessageInfo) makeCoderMethods(t reflect.Type, si structInfo) {
return mi.orderedCoderFields[i].num < mi.orderedCoderFields[j].num return mi.orderedCoderFields[i].num < mi.orderedCoderFields[j].num
}) })
var maxDense pref.FieldNumber var maxDense protoreflect.FieldNumber
for _, cf := range mi.orderedCoderFields { for _, cf := range mi.orderedCoderFields {
if cf.num >= 16 && cf.num >= 2*maxDense { if cf.num >= 16 && cf.num >= 2*maxDense {
break break
@@ -175,12 +175,12 @@ func (mi *MessageInfo) makeCoderMethods(t reflect.Type, si structInfo) {
mi.needsInitCheck = needsInitCheck(mi.Desc) mi.needsInitCheck = needsInitCheck(mi.Desc)
if mi.methods.Marshal == nil && mi.methods.Size == nil { if mi.methods.Marshal == nil && mi.methods.Size == nil {
mi.methods.Flags |= piface.SupportMarshalDeterministic mi.methods.Flags |= protoiface.SupportMarshalDeterministic
mi.methods.Marshal = mi.marshal mi.methods.Marshal = mi.marshal
mi.methods.Size = mi.size mi.methods.Size = mi.size
} }
if mi.methods.Unmarshal == nil { if mi.methods.Unmarshal == nil {
mi.methods.Flags |= piface.SupportUnmarshalDiscardUnknown mi.methods.Flags |= protoiface.SupportUnmarshalDiscardUnknown
mi.methods.Unmarshal = mi.unmarshal mi.methods.Unmarshal = mi.unmarshal
} }
if mi.methods.CheckInitialized == nil { if mi.methods.CheckInitialized == nil {

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build purego || appengine
// +build purego appengine // +build purego appengine
package impl package impl

View File

@@ -10,7 +10,7 @@ import (
"google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/encoding/protowire"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
// pointerCoderFuncs is a set of pointer encoding functions. // pointerCoderFuncs is a set of pointer encoding functions.
@@ -25,83 +25,83 @@ type pointerCoderFuncs struct {
// valueCoderFuncs is a set of protoreflect.Value encoding functions. // valueCoderFuncs is a set of protoreflect.Value encoding functions.
type valueCoderFuncs struct { type valueCoderFuncs struct {
size func(v pref.Value, tagsize int, opts marshalOptions) int size func(v protoreflect.Value, tagsize int, opts marshalOptions) int
marshal func(b []byte, v pref.Value, wiretag uint64, opts marshalOptions) ([]byte, error) marshal func(b []byte, v protoreflect.Value, wiretag uint64, opts marshalOptions) ([]byte, error)
unmarshal func(b []byte, v pref.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (pref.Value, unmarshalOutput, error) unmarshal func(b []byte, v protoreflect.Value, num protowire.Number, wtyp protowire.Type, opts unmarshalOptions) (protoreflect.Value, unmarshalOutput, error)
isInit func(v pref.Value) error isInit func(v protoreflect.Value) error
merge func(dst, src pref.Value, opts mergeOptions) pref.Value merge func(dst, src protoreflect.Value, opts mergeOptions) protoreflect.Value
} }
// fieldCoder returns pointer functions for a field, used for operating on // fieldCoder returns pointer functions for a field, used for operating on
// struct fields. // struct fields.
func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointerCoderFuncs) { func fieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointerCoderFuncs) {
switch { switch {
case fd.IsMap(): case fd.IsMap():
return encoderFuncsForMap(fd, ft) return encoderFuncsForMap(fd, ft)
case fd.Cardinality() == pref.Repeated && !fd.IsPacked(): case fd.Cardinality() == protoreflect.Repeated && !fd.IsPacked():
// Repeated fields (not packed). // Repeated fields (not packed).
if ft.Kind() != reflect.Slice { if ft.Kind() != reflect.Slice {
break break
} }
ft := ft.Elem() ft := ft.Elem()
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if ft.Kind() == reflect.Bool { if ft.Kind() == reflect.Bool {
return nil, coderBoolSlice return nil, coderBoolSlice
} }
case pref.EnumKind: case protoreflect.EnumKind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderEnumSlice return nil, coderEnumSlice
} }
case pref.Int32Kind: case protoreflect.Int32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderInt32Slice return nil, coderInt32Slice
} }
case pref.Sint32Kind: case protoreflect.Sint32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSint32Slice return nil, coderSint32Slice
} }
case pref.Uint32Kind: case protoreflect.Uint32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderUint32Slice return nil, coderUint32Slice
} }
case pref.Int64Kind: case protoreflect.Int64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderInt64Slice return nil, coderInt64Slice
} }
case pref.Sint64Kind: case protoreflect.Sint64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSint64Slice return nil, coderSint64Slice
} }
case pref.Uint64Kind: case protoreflect.Uint64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderUint64Slice return nil, coderUint64Slice
} }
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSfixed32Slice return nil, coderSfixed32Slice
} }
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderFixed32Slice return nil, coderFixed32Slice
} }
case pref.FloatKind: case protoreflect.FloatKind:
if ft.Kind() == reflect.Float32 { if ft.Kind() == reflect.Float32 {
return nil, coderFloatSlice return nil, coderFloatSlice
} }
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSfixed64Slice return nil, coderSfixed64Slice
} }
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderFixed64Slice return nil, coderFixed64Slice
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if ft.Kind() == reflect.Float64 { if ft.Kind() == reflect.Float64 {
return nil, coderDoubleSlice return nil, coderDoubleSlice
} }
case pref.StringKind: case protoreflect.StringKind:
if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) { if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) {
return nil, coderStringSliceValidateUTF8 return nil, coderStringSliceValidateUTF8
} }
@@ -114,19 +114,19 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 { if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 {
return nil, coderBytesSlice return nil, coderBytesSlice
} }
case pref.BytesKind: case protoreflect.BytesKind:
if ft.Kind() == reflect.String { if ft.Kind() == reflect.String {
return nil, coderStringSlice return nil, coderStringSlice
} }
if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 { if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 {
return nil, coderBytesSlice return nil, coderBytesSlice
} }
case pref.MessageKind: case protoreflect.MessageKind:
return getMessageInfo(ft), makeMessageSliceFieldCoder(fd, ft) return getMessageInfo(ft), makeMessageSliceFieldCoder(fd, ft)
case pref.GroupKind: case protoreflect.GroupKind:
return getMessageInfo(ft), makeGroupSliceFieldCoder(fd, ft) return getMessageInfo(ft), makeGroupSliceFieldCoder(fd, ft)
} }
case fd.Cardinality() == pref.Repeated && fd.IsPacked(): case fd.Cardinality() == protoreflect.Repeated && fd.IsPacked():
// Packed repeated fields. // Packed repeated fields.
// //
// Only repeated fields of primitive numeric types // Only repeated fields of primitive numeric types
@@ -136,128 +136,128 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
} }
ft := ft.Elem() ft := ft.Elem()
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if ft.Kind() == reflect.Bool { if ft.Kind() == reflect.Bool {
return nil, coderBoolPackedSlice return nil, coderBoolPackedSlice
} }
case pref.EnumKind: case protoreflect.EnumKind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderEnumPackedSlice return nil, coderEnumPackedSlice
} }
case pref.Int32Kind: case protoreflect.Int32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderInt32PackedSlice return nil, coderInt32PackedSlice
} }
case pref.Sint32Kind: case protoreflect.Sint32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSint32PackedSlice return nil, coderSint32PackedSlice
} }
case pref.Uint32Kind: case protoreflect.Uint32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderUint32PackedSlice return nil, coderUint32PackedSlice
} }
case pref.Int64Kind: case protoreflect.Int64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderInt64PackedSlice return nil, coderInt64PackedSlice
} }
case pref.Sint64Kind: case protoreflect.Sint64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSint64PackedSlice return nil, coderSint64PackedSlice
} }
case pref.Uint64Kind: case protoreflect.Uint64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderUint64PackedSlice return nil, coderUint64PackedSlice
} }
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSfixed32PackedSlice return nil, coderSfixed32PackedSlice
} }
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderFixed32PackedSlice return nil, coderFixed32PackedSlice
} }
case pref.FloatKind: case protoreflect.FloatKind:
if ft.Kind() == reflect.Float32 { if ft.Kind() == reflect.Float32 {
return nil, coderFloatPackedSlice return nil, coderFloatPackedSlice
} }
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSfixed64PackedSlice return nil, coderSfixed64PackedSlice
} }
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderFixed64PackedSlice return nil, coderFixed64PackedSlice
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if ft.Kind() == reflect.Float64 { if ft.Kind() == reflect.Float64 {
return nil, coderDoublePackedSlice return nil, coderDoublePackedSlice
} }
} }
case fd.Kind() == pref.MessageKind: case fd.Kind() == protoreflect.MessageKind:
return getMessageInfo(ft), makeMessageFieldCoder(fd, ft) return getMessageInfo(ft), makeMessageFieldCoder(fd, ft)
case fd.Kind() == pref.GroupKind: case fd.Kind() == protoreflect.GroupKind:
return getMessageInfo(ft), makeGroupFieldCoder(fd, ft) return getMessageInfo(ft), makeGroupFieldCoder(fd, ft)
case fd.Syntax() == pref.Proto3 && fd.ContainingOneof() == nil: case !fd.HasPresence() && fd.ContainingOneof() == nil:
// Populated oneof fields always encode even if set to the zero value, // Populated oneof fields always encode even if set to the zero value,
// which normally are not encoded in proto3. // which normally are not encoded in proto3.
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if ft.Kind() == reflect.Bool { if ft.Kind() == reflect.Bool {
return nil, coderBoolNoZero return nil, coderBoolNoZero
} }
case pref.EnumKind: case protoreflect.EnumKind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderEnumNoZero return nil, coderEnumNoZero
} }
case pref.Int32Kind: case protoreflect.Int32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderInt32NoZero return nil, coderInt32NoZero
} }
case pref.Sint32Kind: case protoreflect.Sint32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSint32NoZero return nil, coderSint32NoZero
} }
case pref.Uint32Kind: case protoreflect.Uint32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderUint32NoZero return nil, coderUint32NoZero
} }
case pref.Int64Kind: case protoreflect.Int64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderInt64NoZero return nil, coderInt64NoZero
} }
case pref.Sint64Kind: case protoreflect.Sint64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSint64NoZero return nil, coderSint64NoZero
} }
case pref.Uint64Kind: case protoreflect.Uint64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderUint64NoZero return nil, coderUint64NoZero
} }
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSfixed32NoZero return nil, coderSfixed32NoZero
} }
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderFixed32NoZero return nil, coderFixed32NoZero
} }
case pref.FloatKind: case protoreflect.FloatKind:
if ft.Kind() == reflect.Float32 { if ft.Kind() == reflect.Float32 {
return nil, coderFloatNoZero return nil, coderFloatNoZero
} }
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSfixed64NoZero return nil, coderSfixed64NoZero
} }
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderFixed64NoZero return nil, coderFixed64NoZero
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if ft.Kind() == reflect.Float64 { if ft.Kind() == reflect.Float64 {
return nil, coderDoubleNoZero return nil, coderDoubleNoZero
} }
case pref.StringKind: case protoreflect.StringKind:
if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) { if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) {
return nil, coderStringNoZeroValidateUTF8 return nil, coderStringNoZeroValidateUTF8
} }
@@ -270,7 +270,7 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 { if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 {
return nil, coderBytesNoZero return nil, coderBytesNoZero
} }
case pref.BytesKind: case protoreflect.BytesKind:
if ft.Kind() == reflect.String { if ft.Kind() == reflect.String {
return nil, coderStringNoZero return nil, coderStringNoZero
} }
@@ -281,133 +281,133 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
case ft.Kind() == reflect.Ptr: case ft.Kind() == reflect.Ptr:
ft := ft.Elem() ft := ft.Elem()
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if ft.Kind() == reflect.Bool { if ft.Kind() == reflect.Bool {
return nil, coderBoolPtr return nil, coderBoolPtr
} }
case pref.EnumKind: case protoreflect.EnumKind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderEnumPtr return nil, coderEnumPtr
} }
case pref.Int32Kind: case protoreflect.Int32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderInt32Ptr return nil, coderInt32Ptr
} }
case pref.Sint32Kind: case protoreflect.Sint32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSint32Ptr return nil, coderSint32Ptr
} }
case pref.Uint32Kind: case protoreflect.Uint32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderUint32Ptr return nil, coderUint32Ptr
} }
case pref.Int64Kind: case protoreflect.Int64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderInt64Ptr return nil, coderInt64Ptr
} }
case pref.Sint64Kind: case protoreflect.Sint64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSint64Ptr return nil, coderSint64Ptr
} }
case pref.Uint64Kind: case protoreflect.Uint64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderUint64Ptr return nil, coderUint64Ptr
} }
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSfixed32Ptr return nil, coderSfixed32Ptr
} }
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderFixed32Ptr return nil, coderFixed32Ptr
} }
case pref.FloatKind: case protoreflect.FloatKind:
if ft.Kind() == reflect.Float32 { if ft.Kind() == reflect.Float32 {
return nil, coderFloatPtr return nil, coderFloatPtr
} }
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSfixed64Ptr return nil, coderSfixed64Ptr
} }
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderFixed64Ptr return nil, coderFixed64Ptr
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if ft.Kind() == reflect.Float64 { if ft.Kind() == reflect.Float64 {
return nil, coderDoublePtr return nil, coderDoublePtr
} }
case pref.StringKind: case protoreflect.StringKind:
if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) { if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) {
return nil, coderStringPtrValidateUTF8 return nil, coderStringPtrValidateUTF8
} }
if ft.Kind() == reflect.String { if ft.Kind() == reflect.String {
return nil, coderStringPtr return nil, coderStringPtr
} }
case pref.BytesKind: case protoreflect.BytesKind:
if ft.Kind() == reflect.String { if ft.Kind() == reflect.String {
return nil, coderStringPtr return nil, coderStringPtr
} }
} }
default: default:
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if ft.Kind() == reflect.Bool { if ft.Kind() == reflect.Bool {
return nil, coderBool return nil, coderBool
} }
case pref.EnumKind: case protoreflect.EnumKind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderEnum return nil, coderEnum
} }
case pref.Int32Kind: case protoreflect.Int32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderInt32 return nil, coderInt32
} }
case pref.Sint32Kind: case protoreflect.Sint32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSint32 return nil, coderSint32
} }
case pref.Uint32Kind: case protoreflect.Uint32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderUint32 return nil, coderUint32
} }
case pref.Int64Kind: case protoreflect.Int64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderInt64 return nil, coderInt64
} }
case pref.Sint64Kind: case protoreflect.Sint64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSint64 return nil, coderSint64
} }
case pref.Uint64Kind: case protoreflect.Uint64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderUint64 return nil, coderUint64
} }
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
if ft.Kind() == reflect.Int32 { if ft.Kind() == reflect.Int32 {
return nil, coderSfixed32 return nil, coderSfixed32
} }
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
if ft.Kind() == reflect.Uint32 { if ft.Kind() == reflect.Uint32 {
return nil, coderFixed32 return nil, coderFixed32
} }
case pref.FloatKind: case protoreflect.FloatKind:
if ft.Kind() == reflect.Float32 { if ft.Kind() == reflect.Float32 {
return nil, coderFloat return nil, coderFloat
} }
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
if ft.Kind() == reflect.Int64 { if ft.Kind() == reflect.Int64 {
return nil, coderSfixed64 return nil, coderSfixed64
} }
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
if ft.Kind() == reflect.Uint64 { if ft.Kind() == reflect.Uint64 {
return nil, coderFixed64 return nil, coderFixed64
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if ft.Kind() == reflect.Float64 { if ft.Kind() == reflect.Float64 {
return nil, coderDouble return nil, coderDouble
} }
case pref.StringKind: case protoreflect.StringKind:
if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) { if ft.Kind() == reflect.String && strs.EnforceUTF8(fd) {
return nil, coderStringValidateUTF8 return nil, coderStringValidateUTF8
} }
@@ -420,7 +420,7 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 { if ft.Kind() == reflect.Slice && ft.Elem().Kind() == reflect.Uint8 {
return nil, coderBytes return nil, coderBytes
} }
case pref.BytesKind: case protoreflect.BytesKind:
if ft.Kind() == reflect.String { if ft.Kind() == reflect.String {
return nil, coderString return nil, coderString
} }
@@ -434,122 +434,122 @@ func fieldCoder(fd pref.FieldDescriptor, ft reflect.Type) (*MessageInfo, pointer
// encoderFuncsForValue returns value functions for a field, used for // encoderFuncsForValue returns value functions for a field, used for
// extension values and map encoding. // extension values and map encoding.
func encoderFuncsForValue(fd pref.FieldDescriptor) valueCoderFuncs { func encoderFuncsForValue(fd protoreflect.FieldDescriptor) valueCoderFuncs {
switch { switch {
case fd.Cardinality() == pref.Repeated && !fd.IsPacked(): case fd.Cardinality() == protoreflect.Repeated && !fd.IsPacked():
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
return coderBoolSliceValue return coderBoolSliceValue
case pref.EnumKind: case protoreflect.EnumKind:
return coderEnumSliceValue return coderEnumSliceValue
case pref.Int32Kind: case protoreflect.Int32Kind:
return coderInt32SliceValue return coderInt32SliceValue
case pref.Sint32Kind: case protoreflect.Sint32Kind:
return coderSint32SliceValue return coderSint32SliceValue
case pref.Uint32Kind: case protoreflect.Uint32Kind:
return coderUint32SliceValue return coderUint32SliceValue
case pref.Int64Kind: case protoreflect.Int64Kind:
return coderInt64SliceValue return coderInt64SliceValue
case pref.Sint64Kind: case protoreflect.Sint64Kind:
return coderSint64SliceValue return coderSint64SliceValue
case pref.Uint64Kind: case protoreflect.Uint64Kind:
return coderUint64SliceValue return coderUint64SliceValue
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
return coderSfixed32SliceValue return coderSfixed32SliceValue
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
return coderFixed32SliceValue return coderFixed32SliceValue
case pref.FloatKind: case protoreflect.FloatKind:
return coderFloatSliceValue return coderFloatSliceValue
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
return coderSfixed64SliceValue return coderSfixed64SliceValue
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
return coderFixed64SliceValue return coderFixed64SliceValue
case pref.DoubleKind: case protoreflect.DoubleKind:
return coderDoubleSliceValue return coderDoubleSliceValue
case pref.StringKind: case protoreflect.StringKind:
// We don't have a UTF-8 validating coder for repeated string fields. // We don't have a UTF-8 validating coder for repeated string fields.
// Value coders are used for extensions and maps. // Value coders are used for extensions and maps.
// Extensions are never proto3, and maps never contain lists. // Extensions are never proto3, and maps never contain lists.
return coderStringSliceValue return coderStringSliceValue
case pref.BytesKind: case protoreflect.BytesKind:
return coderBytesSliceValue return coderBytesSliceValue
case pref.MessageKind: case protoreflect.MessageKind:
return coderMessageSliceValue return coderMessageSliceValue
case pref.GroupKind: case protoreflect.GroupKind:
return coderGroupSliceValue return coderGroupSliceValue
} }
case fd.Cardinality() == pref.Repeated && fd.IsPacked(): case fd.Cardinality() == protoreflect.Repeated && fd.IsPacked():
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
return coderBoolPackedSliceValue return coderBoolPackedSliceValue
case pref.EnumKind: case protoreflect.EnumKind:
return coderEnumPackedSliceValue return coderEnumPackedSliceValue
case pref.Int32Kind: case protoreflect.Int32Kind:
return coderInt32PackedSliceValue return coderInt32PackedSliceValue
case pref.Sint32Kind: case protoreflect.Sint32Kind:
return coderSint32PackedSliceValue return coderSint32PackedSliceValue
case pref.Uint32Kind: case protoreflect.Uint32Kind:
return coderUint32PackedSliceValue return coderUint32PackedSliceValue
case pref.Int64Kind: case protoreflect.Int64Kind:
return coderInt64PackedSliceValue return coderInt64PackedSliceValue
case pref.Sint64Kind: case protoreflect.Sint64Kind:
return coderSint64PackedSliceValue return coderSint64PackedSliceValue
case pref.Uint64Kind: case protoreflect.Uint64Kind:
return coderUint64PackedSliceValue return coderUint64PackedSliceValue
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
return coderSfixed32PackedSliceValue return coderSfixed32PackedSliceValue
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
return coderFixed32PackedSliceValue return coderFixed32PackedSliceValue
case pref.FloatKind: case protoreflect.FloatKind:
return coderFloatPackedSliceValue return coderFloatPackedSliceValue
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
return coderSfixed64PackedSliceValue return coderSfixed64PackedSliceValue
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
return coderFixed64PackedSliceValue return coderFixed64PackedSliceValue
case pref.DoubleKind: case protoreflect.DoubleKind:
return coderDoublePackedSliceValue return coderDoublePackedSliceValue
} }
default: default:
switch fd.Kind() { switch fd.Kind() {
default: default:
case pref.BoolKind: case protoreflect.BoolKind:
return coderBoolValue return coderBoolValue
case pref.EnumKind: case protoreflect.EnumKind:
return coderEnumValue return coderEnumValue
case pref.Int32Kind: case protoreflect.Int32Kind:
return coderInt32Value return coderInt32Value
case pref.Sint32Kind: case protoreflect.Sint32Kind:
return coderSint32Value return coderSint32Value
case pref.Uint32Kind: case protoreflect.Uint32Kind:
return coderUint32Value return coderUint32Value
case pref.Int64Kind: case protoreflect.Int64Kind:
return coderInt64Value return coderInt64Value
case pref.Sint64Kind: case protoreflect.Sint64Kind:
return coderSint64Value return coderSint64Value
case pref.Uint64Kind: case protoreflect.Uint64Kind:
return coderUint64Value return coderUint64Value
case pref.Sfixed32Kind: case protoreflect.Sfixed32Kind:
return coderSfixed32Value return coderSfixed32Value
case pref.Fixed32Kind: case protoreflect.Fixed32Kind:
return coderFixed32Value return coderFixed32Value
case pref.FloatKind: case protoreflect.FloatKind:
return coderFloatValue return coderFloatValue
case pref.Sfixed64Kind: case protoreflect.Sfixed64Kind:
return coderSfixed64Value return coderSfixed64Value
case pref.Fixed64Kind: case protoreflect.Fixed64Kind:
return coderFixed64Value return coderFixed64Value
case pref.DoubleKind: case protoreflect.DoubleKind:
return coderDoubleValue return coderDoubleValue
case pref.StringKind: case protoreflect.StringKind:
if strs.EnforceUTF8(fd) { if strs.EnforceUTF8(fd) {
return coderStringValueValidateUTF8 return coderStringValueValidateUTF8
} }
return coderStringValue return coderStringValue
case pref.BytesKind: case protoreflect.BytesKind:
return coderBytesValue return coderBytesValue
case pref.MessageKind: case protoreflect.MessageKind:
return coderMessageValue return coderMessageValue
case pref.GroupKind: case protoreflect.GroupKind:
return coderGroupValue return coderGroupValue
} }
} }

View File

@@ -2,6 +2,7 @@
// Use of this source code is governed by a BSD-style // Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file. // license that can be found in the LICENSE file.
//go:build !purego && !appengine
// +build !purego,!appengine // +build !purego,!appengine
package impl package impl

View File

@@ -8,7 +8,7 @@ import (
"fmt" "fmt"
"reflect" "reflect"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
// unwrapper unwraps the value to the underlying value. // unwrapper unwraps the value to the underlying value.
@@ -20,13 +20,13 @@ type unwrapper interface {
// A Converter coverts to/from Go reflect.Value types and protobuf protoreflect.Value types. // A Converter coverts to/from Go reflect.Value types and protobuf protoreflect.Value types.
type Converter interface { type Converter interface {
// PBValueOf converts a reflect.Value to a protoreflect.Value. // PBValueOf converts a reflect.Value to a protoreflect.Value.
PBValueOf(reflect.Value) pref.Value PBValueOf(reflect.Value) protoreflect.Value
// GoValueOf converts a protoreflect.Value to a reflect.Value. // GoValueOf converts a protoreflect.Value to a reflect.Value.
GoValueOf(pref.Value) reflect.Value GoValueOf(protoreflect.Value) reflect.Value
// IsValidPB returns whether a protoreflect.Value is compatible with this type. // IsValidPB returns whether a protoreflect.Value is compatible with this type.
IsValidPB(pref.Value) bool IsValidPB(protoreflect.Value) bool
// IsValidGo returns whether a reflect.Value is compatible with this type. // IsValidGo returns whether a reflect.Value is compatible with this type.
IsValidGo(reflect.Value) bool IsValidGo(reflect.Value) bool
@@ -34,12 +34,12 @@ type Converter interface {
// New returns a new field value. // New returns a new field value.
// For scalars, it returns the default value of the field. // For scalars, it returns the default value of the field.
// For composite types, it returns a new mutable value. // For composite types, it returns a new mutable value.
New() pref.Value New() protoreflect.Value
// Zero returns a new field value. // Zero returns a new field value.
// For scalars, it returns the default value of the field. // For scalars, it returns the default value of the field.
// For composite types, it returns an immutable, empty value. // For composite types, it returns an immutable, empty value.
Zero() pref.Value Zero() protoreflect.Value
} }
// NewConverter matches a Go type with a protobuf field and returns a Converter // NewConverter matches a Go type with a protobuf field and returns a Converter
@@ -50,7 +50,7 @@ type Converter interface {
// This matcher deliberately supports a wider range of Go types than what // This matcher deliberately supports a wider range of Go types than what
// protoc-gen-go historically generated to be able to automatically wrap some // protoc-gen-go historically generated to be able to automatically wrap some
// v1 messages generated by other forks of protoc-gen-go. // v1 messages generated by other forks of protoc-gen-go.
func NewConverter(t reflect.Type, fd pref.FieldDescriptor) Converter { func NewConverter(t reflect.Type, fd protoreflect.FieldDescriptor) Converter {
switch { switch {
case fd.IsList(): case fd.IsList():
return newListConverter(t, fd) return newListConverter(t, fd)
@@ -59,7 +59,6 @@ func NewConverter(t reflect.Type, fd pref.FieldDescriptor) Converter {
default: default:
return newSingularConverter(t, fd) return newSingularConverter(t, fd)
} }
panic(fmt.Sprintf("invalid Go type %v for field %v", t, fd.FullName()))
} }
var ( var (
@@ -76,68 +75,68 @@ var (
) )
var ( var (
boolZero = pref.ValueOfBool(false) boolZero = protoreflect.ValueOfBool(false)
int32Zero = pref.ValueOfInt32(0) int32Zero = protoreflect.ValueOfInt32(0)
int64Zero = pref.ValueOfInt64(0) int64Zero = protoreflect.ValueOfInt64(0)
uint32Zero = pref.ValueOfUint32(0) uint32Zero = protoreflect.ValueOfUint32(0)
uint64Zero = pref.ValueOfUint64(0) uint64Zero = protoreflect.ValueOfUint64(0)
float32Zero = pref.ValueOfFloat32(0) float32Zero = protoreflect.ValueOfFloat32(0)
float64Zero = pref.ValueOfFloat64(0) float64Zero = protoreflect.ValueOfFloat64(0)
stringZero = pref.ValueOfString("") stringZero = protoreflect.ValueOfString("")
bytesZero = pref.ValueOfBytes(nil) bytesZero = protoreflect.ValueOfBytes(nil)
) )
func newSingularConverter(t reflect.Type, fd pref.FieldDescriptor) Converter { func newSingularConverter(t reflect.Type, fd protoreflect.FieldDescriptor) Converter {
defVal := func(fd pref.FieldDescriptor, zero pref.Value) pref.Value { defVal := func(fd protoreflect.FieldDescriptor, zero protoreflect.Value) protoreflect.Value {
if fd.Cardinality() == pref.Repeated { if fd.Cardinality() == protoreflect.Repeated {
// Default isn't defined for repeated fields. // Default isn't defined for repeated fields.
return zero return zero
} }
return fd.Default() return fd.Default()
} }
switch fd.Kind() { switch fd.Kind() {
case pref.BoolKind: case protoreflect.BoolKind:
if t.Kind() == reflect.Bool { if t.Kind() == reflect.Bool {
return &boolConverter{t, defVal(fd, boolZero)} return &boolConverter{t, defVal(fd, boolZero)}
} }
case pref.Int32Kind, pref.Sint32Kind, pref.Sfixed32Kind: case protoreflect.Int32Kind, protoreflect.Sint32Kind, protoreflect.Sfixed32Kind:
if t.Kind() == reflect.Int32 { if t.Kind() == reflect.Int32 {
return &int32Converter{t, defVal(fd, int32Zero)} return &int32Converter{t, defVal(fd, int32Zero)}
} }
case pref.Int64Kind, pref.Sint64Kind, pref.Sfixed64Kind: case protoreflect.Int64Kind, protoreflect.Sint64Kind, protoreflect.Sfixed64Kind:
if t.Kind() == reflect.Int64 { if t.Kind() == reflect.Int64 {
return &int64Converter{t, defVal(fd, int64Zero)} return &int64Converter{t, defVal(fd, int64Zero)}
} }
case pref.Uint32Kind, pref.Fixed32Kind: case protoreflect.Uint32Kind, protoreflect.Fixed32Kind:
if t.Kind() == reflect.Uint32 { if t.Kind() == reflect.Uint32 {
return &uint32Converter{t, defVal(fd, uint32Zero)} return &uint32Converter{t, defVal(fd, uint32Zero)}
} }
case pref.Uint64Kind, pref.Fixed64Kind: case protoreflect.Uint64Kind, protoreflect.Fixed64Kind:
if t.Kind() == reflect.Uint64 { if t.Kind() == reflect.Uint64 {
return &uint64Converter{t, defVal(fd, uint64Zero)} return &uint64Converter{t, defVal(fd, uint64Zero)}
} }
case pref.FloatKind: case protoreflect.FloatKind:
if t.Kind() == reflect.Float32 { if t.Kind() == reflect.Float32 {
return &float32Converter{t, defVal(fd, float32Zero)} return &float32Converter{t, defVal(fd, float32Zero)}
} }
case pref.DoubleKind: case protoreflect.DoubleKind:
if t.Kind() == reflect.Float64 { if t.Kind() == reflect.Float64 {
return &float64Converter{t, defVal(fd, float64Zero)} return &float64Converter{t, defVal(fd, float64Zero)}
} }
case pref.StringKind: case protoreflect.StringKind:
if t.Kind() == reflect.String || (t.Kind() == reflect.Slice && t.Elem() == byteType) { if t.Kind() == reflect.String || (t.Kind() == reflect.Slice && t.Elem() == byteType) {
return &stringConverter{t, defVal(fd, stringZero)} return &stringConverter{t, defVal(fd, stringZero)}
} }
case pref.BytesKind: case protoreflect.BytesKind:
if t.Kind() == reflect.String || (t.Kind() == reflect.Slice && t.Elem() == byteType) { if t.Kind() == reflect.String || (t.Kind() == reflect.Slice && t.Elem() == byteType) {
return &bytesConverter{t, defVal(fd, bytesZero)} return &bytesConverter{t, defVal(fd, bytesZero)}
} }
case pref.EnumKind: case protoreflect.EnumKind:
// Handle enums, which must be a named int32 type. // Handle enums, which must be a named int32 type.
if t.Kind() == reflect.Int32 { if t.Kind() == reflect.Int32 {
return newEnumConverter(t, fd) return newEnumConverter(t, fd)
} }
case pref.MessageKind, pref.GroupKind: case protoreflect.MessageKind, protoreflect.GroupKind:
return newMessageConverter(t) return newMessageConverter(t)
} }
panic(fmt.Sprintf("invalid Go type %v for field %v", t, fd.FullName())) panic(fmt.Sprintf("invalid Go type %v for field %v", t, fd.FullName()))
@@ -145,184 +144,184 @@ func newSingularConverter(t reflect.Type, fd pref.FieldDescriptor) Converter {
type boolConverter struct { type boolConverter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *boolConverter) PBValueOf(v reflect.Value) pref.Value { func (c *boolConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfBool(v.Bool()) return protoreflect.ValueOfBool(v.Bool())
} }
func (c *boolConverter) GoValueOf(v pref.Value) reflect.Value { func (c *boolConverter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(v.Bool()).Convert(c.goType) return reflect.ValueOf(v.Bool()).Convert(c.goType)
} }
func (c *boolConverter) IsValidPB(v pref.Value) bool { func (c *boolConverter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(bool) _, ok := v.Interface().(bool)
return ok return ok
} }
func (c *boolConverter) IsValidGo(v reflect.Value) bool { func (c *boolConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *boolConverter) New() pref.Value { return c.def } func (c *boolConverter) New() protoreflect.Value { return c.def }
func (c *boolConverter) Zero() pref.Value { return c.def } func (c *boolConverter) Zero() protoreflect.Value { return c.def }
type int32Converter struct { type int32Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *int32Converter) PBValueOf(v reflect.Value) pref.Value { func (c *int32Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfInt32(int32(v.Int())) return protoreflect.ValueOfInt32(int32(v.Int()))
} }
func (c *int32Converter) GoValueOf(v pref.Value) reflect.Value { func (c *int32Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(int32(v.Int())).Convert(c.goType) return reflect.ValueOf(int32(v.Int())).Convert(c.goType)
} }
func (c *int32Converter) IsValidPB(v pref.Value) bool { func (c *int32Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(int32) _, ok := v.Interface().(int32)
return ok return ok
} }
func (c *int32Converter) IsValidGo(v reflect.Value) bool { func (c *int32Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *int32Converter) New() pref.Value { return c.def } func (c *int32Converter) New() protoreflect.Value { return c.def }
func (c *int32Converter) Zero() pref.Value { return c.def } func (c *int32Converter) Zero() protoreflect.Value { return c.def }
type int64Converter struct { type int64Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *int64Converter) PBValueOf(v reflect.Value) pref.Value { func (c *int64Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfInt64(int64(v.Int())) return protoreflect.ValueOfInt64(int64(v.Int()))
} }
func (c *int64Converter) GoValueOf(v pref.Value) reflect.Value { func (c *int64Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(int64(v.Int())).Convert(c.goType) return reflect.ValueOf(int64(v.Int())).Convert(c.goType)
} }
func (c *int64Converter) IsValidPB(v pref.Value) bool { func (c *int64Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(int64) _, ok := v.Interface().(int64)
return ok return ok
} }
func (c *int64Converter) IsValidGo(v reflect.Value) bool { func (c *int64Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *int64Converter) New() pref.Value { return c.def } func (c *int64Converter) New() protoreflect.Value { return c.def }
func (c *int64Converter) Zero() pref.Value { return c.def } func (c *int64Converter) Zero() protoreflect.Value { return c.def }
type uint32Converter struct { type uint32Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *uint32Converter) PBValueOf(v reflect.Value) pref.Value { func (c *uint32Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfUint32(uint32(v.Uint())) return protoreflect.ValueOfUint32(uint32(v.Uint()))
} }
func (c *uint32Converter) GoValueOf(v pref.Value) reflect.Value { func (c *uint32Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(uint32(v.Uint())).Convert(c.goType) return reflect.ValueOf(uint32(v.Uint())).Convert(c.goType)
} }
func (c *uint32Converter) IsValidPB(v pref.Value) bool { func (c *uint32Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(uint32) _, ok := v.Interface().(uint32)
return ok return ok
} }
func (c *uint32Converter) IsValidGo(v reflect.Value) bool { func (c *uint32Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *uint32Converter) New() pref.Value { return c.def } func (c *uint32Converter) New() protoreflect.Value { return c.def }
func (c *uint32Converter) Zero() pref.Value { return c.def } func (c *uint32Converter) Zero() protoreflect.Value { return c.def }
type uint64Converter struct { type uint64Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *uint64Converter) PBValueOf(v reflect.Value) pref.Value { func (c *uint64Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfUint64(uint64(v.Uint())) return protoreflect.ValueOfUint64(uint64(v.Uint()))
} }
func (c *uint64Converter) GoValueOf(v pref.Value) reflect.Value { func (c *uint64Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(uint64(v.Uint())).Convert(c.goType) return reflect.ValueOf(uint64(v.Uint())).Convert(c.goType)
} }
func (c *uint64Converter) IsValidPB(v pref.Value) bool { func (c *uint64Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(uint64) _, ok := v.Interface().(uint64)
return ok return ok
} }
func (c *uint64Converter) IsValidGo(v reflect.Value) bool { func (c *uint64Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *uint64Converter) New() pref.Value { return c.def } func (c *uint64Converter) New() protoreflect.Value { return c.def }
func (c *uint64Converter) Zero() pref.Value { return c.def } func (c *uint64Converter) Zero() protoreflect.Value { return c.def }
type float32Converter struct { type float32Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *float32Converter) PBValueOf(v reflect.Value) pref.Value { func (c *float32Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfFloat32(float32(v.Float())) return protoreflect.ValueOfFloat32(float32(v.Float()))
} }
func (c *float32Converter) GoValueOf(v pref.Value) reflect.Value { func (c *float32Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(float32(v.Float())).Convert(c.goType) return reflect.ValueOf(float32(v.Float())).Convert(c.goType)
} }
func (c *float32Converter) IsValidPB(v pref.Value) bool { func (c *float32Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(float32) _, ok := v.Interface().(float32)
return ok return ok
} }
func (c *float32Converter) IsValidGo(v reflect.Value) bool { func (c *float32Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *float32Converter) New() pref.Value { return c.def } func (c *float32Converter) New() protoreflect.Value { return c.def }
func (c *float32Converter) Zero() pref.Value { return c.def } func (c *float32Converter) Zero() protoreflect.Value { return c.def }
type float64Converter struct { type float64Converter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *float64Converter) PBValueOf(v reflect.Value) pref.Value { func (c *float64Converter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfFloat64(float64(v.Float())) return protoreflect.ValueOfFloat64(float64(v.Float()))
} }
func (c *float64Converter) GoValueOf(v pref.Value) reflect.Value { func (c *float64Converter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(float64(v.Float())).Convert(c.goType) return reflect.ValueOf(float64(v.Float())).Convert(c.goType)
} }
func (c *float64Converter) IsValidPB(v pref.Value) bool { func (c *float64Converter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(float64) _, ok := v.Interface().(float64)
return ok return ok
} }
func (c *float64Converter) IsValidGo(v reflect.Value) bool { func (c *float64Converter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *float64Converter) New() pref.Value { return c.def } func (c *float64Converter) New() protoreflect.Value { return c.def }
func (c *float64Converter) Zero() pref.Value { return c.def } func (c *float64Converter) Zero() protoreflect.Value { return c.def }
type stringConverter struct { type stringConverter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *stringConverter) PBValueOf(v reflect.Value) pref.Value { func (c *stringConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfString(v.Convert(stringType).String()) return protoreflect.ValueOfString(v.Convert(stringType).String())
} }
func (c *stringConverter) GoValueOf(v pref.Value) reflect.Value { func (c *stringConverter) GoValueOf(v protoreflect.Value) reflect.Value {
// pref.Value.String never panics, so we go through an interface // pref.Value.String never panics, so we go through an interface
// conversion here to check the type. // conversion here to check the type.
s := v.Interface().(string) s := v.Interface().(string)
@@ -331,71 +330,71 @@ func (c *stringConverter) GoValueOf(v pref.Value) reflect.Value {
} }
return reflect.ValueOf(s).Convert(c.goType) return reflect.ValueOf(s).Convert(c.goType)
} }
func (c *stringConverter) IsValidPB(v pref.Value) bool { func (c *stringConverter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(string) _, ok := v.Interface().(string)
return ok return ok
} }
func (c *stringConverter) IsValidGo(v reflect.Value) bool { func (c *stringConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *stringConverter) New() pref.Value { return c.def } func (c *stringConverter) New() protoreflect.Value { return c.def }
func (c *stringConverter) Zero() pref.Value { return c.def } func (c *stringConverter) Zero() protoreflect.Value { return c.def }
type bytesConverter struct { type bytesConverter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func (c *bytesConverter) PBValueOf(v reflect.Value) pref.Value { func (c *bytesConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
if c.goType.Kind() == reflect.String && v.Len() == 0 { if c.goType.Kind() == reflect.String && v.Len() == 0 {
return pref.ValueOfBytes(nil) // ensure empty string is []byte(nil) return protoreflect.ValueOfBytes(nil) // ensure empty string is []byte(nil)
} }
return pref.ValueOfBytes(v.Convert(bytesType).Bytes()) return protoreflect.ValueOfBytes(v.Convert(bytesType).Bytes())
} }
func (c *bytesConverter) GoValueOf(v pref.Value) reflect.Value { func (c *bytesConverter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(v.Bytes()).Convert(c.goType) return reflect.ValueOf(v.Bytes()).Convert(c.goType)
} }
func (c *bytesConverter) IsValidPB(v pref.Value) bool { func (c *bytesConverter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().([]byte) _, ok := v.Interface().([]byte)
return ok return ok
} }
func (c *bytesConverter) IsValidGo(v reflect.Value) bool { func (c *bytesConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *bytesConverter) New() pref.Value { return c.def } func (c *bytesConverter) New() protoreflect.Value { return c.def }
func (c *bytesConverter) Zero() pref.Value { return c.def } func (c *bytesConverter) Zero() protoreflect.Value { return c.def }
type enumConverter struct { type enumConverter struct {
goType reflect.Type goType reflect.Type
def pref.Value def protoreflect.Value
} }
func newEnumConverter(goType reflect.Type, fd pref.FieldDescriptor) Converter { func newEnumConverter(goType reflect.Type, fd protoreflect.FieldDescriptor) Converter {
var def pref.Value var def protoreflect.Value
if fd.Cardinality() == pref.Repeated { if fd.Cardinality() == protoreflect.Repeated {
def = pref.ValueOfEnum(fd.Enum().Values().Get(0).Number()) def = protoreflect.ValueOfEnum(fd.Enum().Values().Get(0).Number())
} else { } else {
def = fd.Default() def = fd.Default()
} }
return &enumConverter{goType, def} return &enumConverter{goType, def}
} }
func (c *enumConverter) PBValueOf(v reflect.Value) pref.Value { func (c *enumConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfEnum(pref.EnumNumber(v.Int())) return protoreflect.ValueOfEnum(protoreflect.EnumNumber(v.Int()))
} }
func (c *enumConverter) GoValueOf(v pref.Value) reflect.Value { func (c *enumConverter) GoValueOf(v protoreflect.Value) reflect.Value {
return reflect.ValueOf(v.Enum()).Convert(c.goType) return reflect.ValueOf(v.Enum()).Convert(c.goType)
} }
func (c *enumConverter) IsValidPB(v pref.Value) bool { func (c *enumConverter) IsValidPB(v protoreflect.Value) bool {
_, ok := v.Interface().(pref.EnumNumber) _, ok := v.Interface().(protoreflect.EnumNumber)
return ok return ok
} }
@@ -403,11 +402,11 @@ func (c *enumConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *enumConverter) New() pref.Value { func (c *enumConverter) New() protoreflect.Value {
return c.def return c.def
} }
func (c *enumConverter) Zero() pref.Value { func (c *enumConverter) Zero() protoreflect.Value {
return c.def return c.def
} }
@@ -419,7 +418,7 @@ func newMessageConverter(goType reflect.Type) Converter {
return &messageConverter{goType} return &messageConverter{goType}
} }
func (c *messageConverter) PBValueOf(v reflect.Value) pref.Value { func (c *messageConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
@@ -430,13 +429,13 @@ func (c *messageConverter) PBValueOf(v reflect.Value) pref.Value {
v = reflect.Zero(reflect.PtrTo(v.Type())) v = reflect.Zero(reflect.PtrTo(v.Type()))
} }
} }
if m, ok := v.Interface().(pref.ProtoMessage); ok { if m, ok := v.Interface().(protoreflect.ProtoMessage); ok {
return pref.ValueOfMessage(m.ProtoReflect()) return protoreflect.ValueOfMessage(m.ProtoReflect())
} }
return pref.ValueOfMessage(legacyWrapMessage(v)) return protoreflect.ValueOfMessage(legacyWrapMessage(v))
} }
func (c *messageConverter) GoValueOf(v pref.Value) reflect.Value { func (c *messageConverter) GoValueOf(v protoreflect.Value) reflect.Value {
m := v.Message() m := v.Message()
var rv reflect.Value var rv reflect.Value
if u, ok := m.(unwrapper); ok { if u, ok := m.(unwrapper); ok {
@@ -460,7 +459,7 @@ func (c *messageConverter) GoValueOf(v pref.Value) reflect.Value {
return rv return rv
} }
func (c *messageConverter) IsValidPB(v pref.Value) bool { func (c *messageConverter) IsValidPB(v protoreflect.Value) bool {
m := v.Message() m := v.Message()
var rv reflect.Value var rv reflect.Value
if u, ok := m.(unwrapper); ok { if u, ok := m.(unwrapper); ok {
@@ -478,14 +477,14 @@ func (c *messageConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *messageConverter) New() pref.Value { func (c *messageConverter) New() protoreflect.Value {
if c.isNonPointer() { if c.isNonPointer() {
return c.PBValueOf(reflect.New(c.goType).Elem()) return c.PBValueOf(reflect.New(c.goType).Elem())
} }
return c.PBValueOf(reflect.New(c.goType.Elem())) return c.PBValueOf(reflect.New(c.goType.Elem()))
} }
func (c *messageConverter) Zero() pref.Value { func (c *messageConverter) Zero() protoreflect.Value {
return c.PBValueOf(reflect.Zero(c.goType)) return c.PBValueOf(reflect.Zero(c.goType))
} }

View File

@@ -8,10 +8,10 @@ import (
"fmt" "fmt"
"reflect" "reflect"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
func newListConverter(t reflect.Type, fd pref.FieldDescriptor) Converter { func newListConverter(t reflect.Type, fd protoreflect.FieldDescriptor) Converter {
switch { switch {
case t.Kind() == reflect.Ptr && t.Elem().Kind() == reflect.Slice: case t.Kind() == reflect.Ptr && t.Elem().Kind() == reflect.Slice:
return &listPtrConverter{t, newSingularConverter(t.Elem().Elem(), fd)} return &listPtrConverter{t, newSingularConverter(t.Elem().Elem(), fd)}
@@ -26,16 +26,16 @@ type listConverter struct {
c Converter c Converter
} }
func (c *listConverter) PBValueOf(v reflect.Value) pref.Value { func (c *listConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
pv := reflect.New(c.goType) pv := reflect.New(c.goType)
pv.Elem().Set(v) pv.Elem().Set(v)
return pref.ValueOfList(&listReflect{pv, c.c}) return protoreflect.ValueOfList(&listReflect{pv, c.c})
} }
func (c *listConverter) GoValueOf(v pref.Value) reflect.Value { func (c *listConverter) GoValueOf(v protoreflect.Value) reflect.Value {
rv := v.List().(*listReflect).v rv := v.List().(*listReflect).v
if rv.IsNil() { if rv.IsNil() {
return reflect.Zero(c.goType) return reflect.Zero(c.goType)
@@ -43,7 +43,7 @@ func (c *listConverter) GoValueOf(v pref.Value) reflect.Value {
return rv.Elem() return rv.Elem()
} }
func (c *listConverter) IsValidPB(v pref.Value) bool { func (c *listConverter) IsValidPB(v protoreflect.Value) bool {
list, ok := v.Interface().(*listReflect) list, ok := v.Interface().(*listReflect)
if !ok { if !ok {
return false return false
@@ -55,12 +55,12 @@ func (c *listConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *listConverter) New() pref.Value { func (c *listConverter) New() protoreflect.Value {
return pref.ValueOfList(&listReflect{reflect.New(c.goType), c.c}) return protoreflect.ValueOfList(&listReflect{reflect.New(c.goType), c.c})
} }
func (c *listConverter) Zero() pref.Value { func (c *listConverter) Zero() protoreflect.Value {
return pref.ValueOfList(&listReflect{reflect.Zero(reflect.PtrTo(c.goType)), c.c}) return protoreflect.ValueOfList(&listReflect{reflect.Zero(reflect.PtrTo(c.goType)), c.c})
} }
type listPtrConverter struct { type listPtrConverter struct {
@@ -68,18 +68,18 @@ type listPtrConverter struct {
c Converter c Converter
} }
func (c *listPtrConverter) PBValueOf(v reflect.Value) pref.Value { func (c *listPtrConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfList(&listReflect{v, c.c}) return protoreflect.ValueOfList(&listReflect{v, c.c})
} }
func (c *listPtrConverter) GoValueOf(v pref.Value) reflect.Value { func (c *listPtrConverter) GoValueOf(v protoreflect.Value) reflect.Value {
return v.List().(*listReflect).v return v.List().(*listReflect).v
} }
func (c *listPtrConverter) IsValidPB(v pref.Value) bool { func (c *listPtrConverter) IsValidPB(v protoreflect.Value) bool {
list, ok := v.Interface().(*listReflect) list, ok := v.Interface().(*listReflect)
if !ok { if !ok {
return false return false
@@ -91,11 +91,11 @@ func (c *listPtrConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *listPtrConverter) New() pref.Value { func (c *listPtrConverter) New() protoreflect.Value {
return c.PBValueOf(reflect.New(c.goType.Elem())) return c.PBValueOf(reflect.New(c.goType.Elem()))
} }
func (c *listPtrConverter) Zero() pref.Value { func (c *listPtrConverter) Zero() protoreflect.Value {
return c.PBValueOf(reflect.Zero(c.goType)) return c.PBValueOf(reflect.Zero(c.goType))
} }
@@ -110,16 +110,16 @@ func (ls *listReflect) Len() int {
} }
return ls.v.Elem().Len() return ls.v.Elem().Len()
} }
func (ls *listReflect) Get(i int) pref.Value { func (ls *listReflect) Get(i int) protoreflect.Value {
return ls.conv.PBValueOf(ls.v.Elem().Index(i)) return ls.conv.PBValueOf(ls.v.Elem().Index(i))
} }
func (ls *listReflect) Set(i int, v pref.Value) { func (ls *listReflect) Set(i int, v protoreflect.Value) {
ls.v.Elem().Index(i).Set(ls.conv.GoValueOf(v)) ls.v.Elem().Index(i).Set(ls.conv.GoValueOf(v))
} }
func (ls *listReflect) Append(v pref.Value) { func (ls *listReflect) Append(v protoreflect.Value) {
ls.v.Elem().Set(reflect.Append(ls.v.Elem(), ls.conv.GoValueOf(v))) ls.v.Elem().Set(reflect.Append(ls.v.Elem(), ls.conv.GoValueOf(v)))
} }
func (ls *listReflect) AppendMutable() pref.Value { func (ls *listReflect) AppendMutable() protoreflect.Value {
if _, ok := ls.conv.(*messageConverter); !ok { if _, ok := ls.conv.(*messageConverter); !ok {
panic("invalid AppendMutable on list with non-message type") panic("invalid AppendMutable on list with non-message type")
} }
@@ -130,7 +130,7 @@ func (ls *listReflect) AppendMutable() pref.Value {
func (ls *listReflect) Truncate(i int) { func (ls *listReflect) Truncate(i int) {
ls.v.Elem().Set(ls.v.Elem().Slice(0, i)) ls.v.Elem().Set(ls.v.Elem().Slice(0, i))
} }
func (ls *listReflect) NewElement() pref.Value { func (ls *listReflect) NewElement() protoreflect.Value {
return ls.conv.New() return ls.conv.New()
} }
func (ls *listReflect) IsValid() bool { func (ls *listReflect) IsValid() bool {

View File

@@ -8,7 +8,7 @@ import (
"fmt" "fmt"
"reflect" "reflect"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
type mapConverter struct { type mapConverter struct {
@@ -16,7 +16,7 @@ type mapConverter struct {
keyConv, valConv Converter keyConv, valConv Converter
} }
func newMapConverter(t reflect.Type, fd pref.FieldDescriptor) *mapConverter { func newMapConverter(t reflect.Type, fd protoreflect.FieldDescriptor) *mapConverter {
if t.Kind() != reflect.Map { if t.Kind() != reflect.Map {
panic(fmt.Sprintf("invalid Go type %v for field %v", t, fd.FullName())) panic(fmt.Sprintf("invalid Go type %v for field %v", t, fd.FullName()))
} }
@@ -27,18 +27,18 @@ func newMapConverter(t reflect.Type, fd pref.FieldDescriptor) *mapConverter {
} }
} }
func (c *mapConverter) PBValueOf(v reflect.Value) pref.Value { func (c *mapConverter) PBValueOf(v reflect.Value) protoreflect.Value {
if v.Type() != c.goType { if v.Type() != c.goType {
panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType)) panic(fmt.Sprintf("invalid type: got %v, want %v", v.Type(), c.goType))
} }
return pref.ValueOfMap(&mapReflect{v, c.keyConv, c.valConv}) return protoreflect.ValueOfMap(&mapReflect{v, c.keyConv, c.valConv})
} }
func (c *mapConverter) GoValueOf(v pref.Value) reflect.Value { func (c *mapConverter) GoValueOf(v protoreflect.Value) reflect.Value {
return v.Map().(*mapReflect).v return v.Map().(*mapReflect).v
} }
func (c *mapConverter) IsValidPB(v pref.Value) bool { func (c *mapConverter) IsValidPB(v protoreflect.Value) bool {
mapv, ok := v.Interface().(*mapReflect) mapv, ok := v.Interface().(*mapReflect)
if !ok { if !ok {
return false return false
@@ -50,11 +50,11 @@ func (c *mapConverter) IsValidGo(v reflect.Value) bool {
return v.IsValid() && v.Type() == c.goType return v.IsValid() && v.Type() == c.goType
} }
func (c *mapConverter) New() pref.Value { func (c *mapConverter) New() protoreflect.Value {
return c.PBValueOf(reflect.MakeMap(c.goType)) return c.PBValueOf(reflect.MakeMap(c.goType))
} }
func (c *mapConverter) Zero() pref.Value { func (c *mapConverter) Zero() protoreflect.Value {
return c.PBValueOf(reflect.Zero(c.goType)) return c.PBValueOf(reflect.Zero(c.goType))
} }
@@ -67,29 +67,29 @@ type mapReflect struct {
func (ms *mapReflect) Len() int { func (ms *mapReflect) Len() int {
return ms.v.Len() return ms.v.Len()
} }
func (ms *mapReflect) Has(k pref.MapKey) bool { func (ms *mapReflect) Has(k protoreflect.MapKey) bool {
rk := ms.keyConv.GoValueOf(k.Value()) rk := ms.keyConv.GoValueOf(k.Value())
rv := ms.v.MapIndex(rk) rv := ms.v.MapIndex(rk)
return rv.IsValid() return rv.IsValid()
} }
func (ms *mapReflect) Get(k pref.MapKey) pref.Value { func (ms *mapReflect) Get(k protoreflect.MapKey) protoreflect.Value {
rk := ms.keyConv.GoValueOf(k.Value()) rk := ms.keyConv.GoValueOf(k.Value())
rv := ms.v.MapIndex(rk) rv := ms.v.MapIndex(rk)
if !rv.IsValid() { if !rv.IsValid() {
return pref.Value{} return protoreflect.Value{}
} }
return ms.valConv.PBValueOf(rv) return ms.valConv.PBValueOf(rv)
} }
func (ms *mapReflect) Set(k pref.MapKey, v pref.Value) { func (ms *mapReflect) Set(k protoreflect.MapKey, v protoreflect.Value) {
rk := ms.keyConv.GoValueOf(k.Value()) rk := ms.keyConv.GoValueOf(k.Value())
rv := ms.valConv.GoValueOf(v) rv := ms.valConv.GoValueOf(v)
ms.v.SetMapIndex(rk, rv) ms.v.SetMapIndex(rk, rv)
} }
func (ms *mapReflect) Clear(k pref.MapKey) { func (ms *mapReflect) Clear(k protoreflect.MapKey) {
rk := ms.keyConv.GoValueOf(k.Value()) rk := ms.keyConv.GoValueOf(k.Value())
ms.v.SetMapIndex(rk, reflect.Value{}) ms.v.SetMapIndex(rk, reflect.Value{})
} }
func (ms *mapReflect) Mutable(k pref.MapKey) pref.Value { func (ms *mapReflect) Mutable(k protoreflect.MapKey) protoreflect.Value {
if _, ok := ms.valConv.(*messageConverter); !ok { if _, ok := ms.valConv.(*messageConverter); !ok {
panic("invalid Mutable on map with non-message value type") panic("invalid Mutable on map with non-message value type")
} }
@@ -100,7 +100,7 @@ func (ms *mapReflect) Mutable(k pref.MapKey) pref.Value {
} }
return v return v
} }
func (ms *mapReflect) Range(f func(pref.MapKey, pref.Value) bool) { func (ms *mapReflect) Range(f func(protoreflect.MapKey, protoreflect.Value) bool) {
iter := mapRange(ms.v) iter := mapRange(ms.v)
for iter.Next() { for iter.Next() {
k := ms.keyConv.PBValueOf(iter.Key()).MapKey() k := ms.keyConv.PBValueOf(iter.Key()).MapKey()
@@ -110,7 +110,7 @@ func (ms *mapReflect) Range(f func(pref.MapKey, pref.Value) bool) {
} }
} }
} }
func (ms *mapReflect) NewValue() pref.Value { func (ms *mapReflect) NewValue() protoreflect.Value {
return ms.valConv.New() return ms.valConv.New()
} }
func (ms *mapReflect) IsValid() bool { func (ms *mapReflect) IsValid() bool {

View File

@@ -12,12 +12,12 @@ import (
"google.golang.org/protobuf/internal/flags" "google.golang.org/protobuf/internal/flags"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
preg "google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
"google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
piface "google.golang.org/protobuf/runtime/protoiface"
) )
var errDecode = errors.New("cannot parse invalid wire-format data") var errDecode = errors.New("cannot parse invalid wire-format data")
var errRecursionDepth = errors.New("exceeded maximum recursion depth")
type unmarshalOptions struct { type unmarshalOptions struct {
flags protoiface.UnmarshalInputFlags flags protoiface.UnmarshalInputFlags
@@ -25,6 +25,7 @@ type unmarshalOptions struct {
FindExtensionByName(field protoreflect.FullName) (protoreflect.ExtensionType, error) FindExtensionByName(field protoreflect.FullName) (protoreflect.ExtensionType, error)
FindExtensionByNumber(message protoreflect.FullName, field protoreflect.FieldNumber) (protoreflect.ExtensionType, error) FindExtensionByNumber(message protoreflect.FullName, field protoreflect.FieldNumber) (protoreflect.ExtensionType, error)
} }
depth int
} }
func (o unmarshalOptions) Options() proto.UnmarshalOptions { func (o unmarshalOptions) Options() proto.UnmarshalOptions {
@@ -36,14 +37,17 @@ func (o unmarshalOptions) Options() proto.UnmarshalOptions {
} }
} }
func (o unmarshalOptions) DiscardUnknown() bool { return o.flags&piface.UnmarshalDiscardUnknown != 0 } func (o unmarshalOptions) DiscardUnknown() bool {
return o.flags&protoiface.UnmarshalDiscardUnknown != 0
}
func (o unmarshalOptions) IsDefault() bool { func (o unmarshalOptions) IsDefault() bool {
return o.flags == 0 && o.resolver == preg.GlobalTypes return o.flags == 0 && o.resolver == protoregistry.GlobalTypes
} }
var lazyUnmarshalOptions = unmarshalOptions{ var lazyUnmarshalOptions = unmarshalOptions{
resolver: preg.GlobalTypes, resolver: protoregistry.GlobalTypes,
depth: protowire.DefaultRecursionLimit,
} }
type unmarshalOutput struct { type unmarshalOutput struct {
@@ -52,7 +56,7 @@ type unmarshalOutput struct {
} }
// unmarshal is protoreflect.Methods.Unmarshal. // unmarshal is protoreflect.Methods.Unmarshal.
func (mi *MessageInfo) unmarshal(in piface.UnmarshalInput) (piface.UnmarshalOutput, error) { func (mi *MessageInfo) unmarshal(in protoiface.UnmarshalInput) (protoiface.UnmarshalOutput, error) {
var p pointer var p pointer
if ms, ok := in.Message.(*messageState); ok { if ms, ok := in.Message.(*messageState); ok {
p = ms.pointer() p = ms.pointer()
@@ -62,12 +66,13 @@ func (mi *MessageInfo) unmarshal(in piface.UnmarshalInput) (piface.UnmarshalOutp
out, err := mi.unmarshalPointer(in.Buf, p, 0, unmarshalOptions{ out, err := mi.unmarshalPointer(in.Buf, p, 0, unmarshalOptions{
flags: in.Flags, flags: in.Flags,
resolver: in.Resolver, resolver: in.Resolver,
depth: in.Depth,
}) })
var flags piface.UnmarshalOutputFlags var flags protoiface.UnmarshalOutputFlags
if out.initialized { if out.initialized {
flags |= piface.UnmarshalInitialized flags |= protoiface.UnmarshalInitialized
} }
return piface.UnmarshalOutput{ return protoiface.UnmarshalOutput{
Flags: flags, Flags: flags,
}, err }, err
} }
@@ -82,6 +87,10 @@ var errUnknown = errors.New("unknown")
func (mi *MessageInfo) unmarshalPointer(b []byte, p pointer, groupTag protowire.Number, opts unmarshalOptions) (out unmarshalOutput, err error) { func (mi *MessageInfo) unmarshalPointer(b []byte, p pointer, groupTag protowire.Number, opts unmarshalOptions) (out unmarshalOutput, err error) {
mi.init() mi.init()
opts.depth--
if opts.depth < 0 {
return out, errRecursionDepth
}
if flags.ProtoLegacy && mi.isMessageSet { if flags.ProtoLegacy && mi.isMessageSet {
return unmarshalMessageSet(mi, b, p, opts) return unmarshalMessageSet(mi, b, p, opts)
} }
@@ -202,7 +211,7 @@ func (mi *MessageInfo) unmarshalExtension(b []byte, num protowire.Number, wtyp p
var err error var err error
xt, err = opts.resolver.FindExtensionByNumber(mi.Desc.FullName(), num) xt, err = opts.resolver.FindExtensionByNumber(mi.Desc.FullName(), num)
if err != nil { if err != nil {
if err == preg.NotFound { if err == protoregistry.NotFound {
return out, errUnknown return out, errUnknown
} }
return out, errors.New("%v: unable to resolve extension %v: %v", mi.Desc.FullName(), num, err) return out, errors.New("%v: unable to resolve extension %v: %v", mi.Desc.FullName(), num, err)

View File

@@ -7,15 +7,15 @@ package impl
import ( import (
"reflect" "reflect"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
) )
type EnumInfo struct { type EnumInfo struct {
GoReflectType reflect.Type // int32 kind GoReflectType reflect.Type // int32 kind
Desc pref.EnumDescriptor Desc protoreflect.EnumDescriptor
} }
func (t *EnumInfo) New(n pref.EnumNumber) pref.Enum { func (t *EnumInfo) New(n protoreflect.EnumNumber) protoreflect.Enum {
return reflect.ValueOf(n).Convert(t.GoReflectType).Interface().(pref.Enum) return reflect.ValueOf(n).Convert(t.GoReflectType).Interface().(protoreflect.Enum)
} }
func (t *EnumInfo) Descriptor() pref.EnumDescriptor { return t.Desc } func (t *EnumInfo) Descriptor() protoreflect.EnumDescriptor { return t.Desc }

View File

@@ -9,8 +9,8 @@ import (
"sync" "sync"
"sync/atomic" "sync/atomic"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
// ExtensionInfo implements ExtensionType. // ExtensionInfo implements ExtensionType.
@@ -45,7 +45,7 @@ type ExtensionInfo struct {
// since the message may no longer implement the MessageV1 interface. // since the message may no longer implement the MessageV1 interface.
// //
// Deprecated: Use the ExtendedType method instead. // Deprecated: Use the ExtendedType method instead.
ExtendedType piface.MessageV1 ExtendedType protoiface.MessageV1
// ExtensionType is the zero value of the extension type. // ExtensionType is the zero value of the extension type.
// //
@@ -83,31 +83,31 @@ const (
extensionInfoFullInit = 2 extensionInfoFullInit = 2
) )
func InitExtensionInfo(xi *ExtensionInfo, xd pref.ExtensionDescriptor, goType reflect.Type) { func InitExtensionInfo(xi *ExtensionInfo, xd protoreflect.ExtensionDescriptor, goType reflect.Type) {
xi.goType = goType xi.goType = goType
xi.desc = extensionTypeDescriptor{xd, xi} xi.desc = extensionTypeDescriptor{xd, xi}
xi.init = extensionInfoDescInit xi.init = extensionInfoDescInit
} }
func (xi *ExtensionInfo) New() pref.Value { func (xi *ExtensionInfo) New() protoreflect.Value {
return xi.lazyInit().New() return xi.lazyInit().New()
} }
func (xi *ExtensionInfo) Zero() pref.Value { func (xi *ExtensionInfo) Zero() protoreflect.Value {
return xi.lazyInit().Zero() return xi.lazyInit().Zero()
} }
func (xi *ExtensionInfo) ValueOf(v interface{}) pref.Value { func (xi *ExtensionInfo) ValueOf(v interface{}) protoreflect.Value {
return xi.lazyInit().PBValueOf(reflect.ValueOf(v)) return xi.lazyInit().PBValueOf(reflect.ValueOf(v))
} }
func (xi *ExtensionInfo) InterfaceOf(v pref.Value) interface{} { func (xi *ExtensionInfo) InterfaceOf(v protoreflect.Value) interface{} {
return xi.lazyInit().GoValueOf(v).Interface() return xi.lazyInit().GoValueOf(v).Interface()
} }
func (xi *ExtensionInfo) IsValidValue(v pref.Value) bool { func (xi *ExtensionInfo) IsValidValue(v protoreflect.Value) bool {
return xi.lazyInit().IsValidPB(v) return xi.lazyInit().IsValidPB(v)
} }
func (xi *ExtensionInfo) IsValidInterface(v interface{}) bool { func (xi *ExtensionInfo) IsValidInterface(v interface{}) bool {
return xi.lazyInit().IsValidGo(reflect.ValueOf(v)) return xi.lazyInit().IsValidGo(reflect.ValueOf(v))
} }
func (xi *ExtensionInfo) TypeDescriptor() pref.ExtensionTypeDescriptor { func (xi *ExtensionInfo) TypeDescriptor() protoreflect.ExtensionTypeDescriptor {
if atomic.LoadUint32(&xi.init) < extensionInfoDescInit { if atomic.LoadUint32(&xi.init) < extensionInfoDescInit {
xi.lazyInitSlow() xi.lazyInitSlow()
} }
@@ -144,13 +144,13 @@ func (xi *ExtensionInfo) lazyInitSlow() {
} }
type extensionTypeDescriptor struct { type extensionTypeDescriptor struct {
pref.ExtensionDescriptor protoreflect.ExtensionDescriptor
xi *ExtensionInfo xi *ExtensionInfo
} }
func (xtd *extensionTypeDescriptor) Type() pref.ExtensionType { func (xtd *extensionTypeDescriptor) Type() protoreflect.ExtensionType {
return xtd.xi return xtd.xi
} }
func (xtd *extensionTypeDescriptor) Descriptor() pref.ExtensionDescriptor { func (xtd *extensionTypeDescriptor) Descriptor() protoreflect.ExtensionDescriptor {
return xtd.ExtensionDescriptor return xtd.ExtensionDescriptor
} }

View File

@@ -13,13 +13,12 @@ import (
"google.golang.org/protobuf/internal/filedesc" "google.golang.org/protobuf/internal/filedesc"
"google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/internal/strs"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
pref "google.golang.org/protobuf/reflect/protoreflect"
) )
// legacyEnumName returns the name of enums used in legacy code. // legacyEnumName returns the name of enums used in legacy code.
// It is neither the protobuf full name nor the qualified Go name, // It is neither the protobuf full name nor the qualified Go name,
// but rather an odd hybrid of both. // but rather an odd hybrid of both.
func legacyEnumName(ed pref.EnumDescriptor) string { func legacyEnumName(ed protoreflect.EnumDescriptor) string {
var protoPkg string var protoPkg string
enumName := string(ed.FullName()) enumName := string(ed.FullName())
if fd := ed.ParentFile(); fd != nil { if fd := ed.ParentFile(); fd != nil {
@@ -34,68 +33,68 @@ func legacyEnumName(ed pref.EnumDescriptor) string {
// legacyWrapEnum wraps v as a protoreflect.Enum, // legacyWrapEnum wraps v as a protoreflect.Enum,
// where v must be a int32 kind and not implement the v2 API already. // where v must be a int32 kind and not implement the v2 API already.
func legacyWrapEnum(v reflect.Value) pref.Enum { func legacyWrapEnum(v reflect.Value) protoreflect.Enum {
et := legacyLoadEnumType(v.Type()) et := legacyLoadEnumType(v.Type())
return et.New(pref.EnumNumber(v.Int())) return et.New(protoreflect.EnumNumber(v.Int()))
} }
var legacyEnumTypeCache sync.Map // map[reflect.Type]protoreflect.EnumType var legacyEnumTypeCache sync.Map // map[reflect.Type]protoreflect.EnumType
// legacyLoadEnumType dynamically loads a protoreflect.EnumType for t, // legacyLoadEnumType dynamically loads a protoreflect.EnumType for t,
// where t must be an int32 kind and not implement the v2 API already. // where t must be an int32 kind and not implement the v2 API already.
func legacyLoadEnumType(t reflect.Type) pref.EnumType { func legacyLoadEnumType(t reflect.Type) protoreflect.EnumType {
// Fast-path: check if a EnumType is cached for this concrete type. // Fast-path: check if a EnumType is cached for this concrete type.
if et, ok := legacyEnumTypeCache.Load(t); ok { if et, ok := legacyEnumTypeCache.Load(t); ok {
return et.(pref.EnumType) return et.(protoreflect.EnumType)
} }
// Slow-path: derive enum descriptor and initialize EnumType. // Slow-path: derive enum descriptor and initialize EnumType.
var et pref.EnumType var et protoreflect.EnumType
ed := LegacyLoadEnumDesc(t) ed := LegacyLoadEnumDesc(t)
et = &legacyEnumType{ et = &legacyEnumType{
desc: ed, desc: ed,
goType: t, goType: t,
} }
if et, ok := legacyEnumTypeCache.LoadOrStore(t, et); ok { if et, ok := legacyEnumTypeCache.LoadOrStore(t, et); ok {
return et.(pref.EnumType) return et.(protoreflect.EnumType)
} }
return et return et
} }
type legacyEnumType struct { type legacyEnumType struct {
desc pref.EnumDescriptor desc protoreflect.EnumDescriptor
goType reflect.Type goType reflect.Type
m sync.Map // map[protoreflect.EnumNumber]proto.Enum m sync.Map // map[protoreflect.EnumNumber]proto.Enum
} }
func (t *legacyEnumType) New(n pref.EnumNumber) pref.Enum { func (t *legacyEnumType) New(n protoreflect.EnumNumber) protoreflect.Enum {
if e, ok := t.m.Load(n); ok { if e, ok := t.m.Load(n); ok {
return e.(pref.Enum) return e.(protoreflect.Enum)
} }
e := &legacyEnumWrapper{num: n, pbTyp: t, goTyp: t.goType} e := &legacyEnumWrapper{num: n, pbTyp: t, goTyp: t.goType}
t.m.Store(n, e) t.m.Store(n, e)
return e return e
} }
func (t *legacyEnumType) Descriptor() pref.EnumDescriptor { func (t *legacyEnumType) Descriptor() protoreflect.EnumDescriptor {
return t.desc return t.desc
} }
type legacyEnumWrapper struct { type legacyEnumWrapper struct {
num pref.EnumNumber num protoreflect.EnumNumber
pbTyp pref.EnumType pbTyp protoreflect.EnumType
goTyp reflect.Type goTyp reflect.Type
} }
func (e *legacyEnumWrapper) Descriptor() pref.EnumDescriptor { func (e *legacyEnumWrapper) Descriptor() protoreflect.EnumDescriptor {
return e.pbTyp.Descriptor() return e.pbTyp.Descriptor()
} }
func (e *legacyEnumWrapper) Type() pref.EnumType { func (e *legacyEnumWrapper) Type() protoreflect.EnumType {
return e.pbTyp return e.pbTyp
} }
func (e *legacyEnumWrapper) Number() pref.EnumNumber { func (e *legacyEnumWrapper) Number() protoreflect.EnumNumber {
return e.num return e.num
} }
func (e *legacyEnumWrapper) ProtoReflect() pref.Enum { func (e *legacyEnumWrapper) ProtoReflect() protoreflect.Enum {
return e return e
} }
func (e *legacyEnumWrapper) protoUnwrap() interface{} { func (e *legacyEnumWrapper) protoUnwrap() interface{} {
@@ -105,7 +104,7 @@ func (e *legacyEnumWrapper) protoUnwrap() interface{} {
} }
var ( var (
_ pref.Enum = (*legacyEnumWrapper)(nil) _ protoreflect.Enum = (*legacyEnumWrapper)(nil)
_ unwrapper = (*legacyEnumWrapper)(nil) _ unwrapper = (*legacyEnumWrapper)(nil)
) )
@@ -115,15 +114,15 @@ var legacyEnumDescCache sync.Map // map[reflect.Type]protoreflect.EnumDescriptor
// which must be an int32 kind and not implement the v2 API already. // which must be an int32 kind and not implement the v2 API already.
// //
// This is exported for testing purposes. // This is exported for testing purposes.
func LegacyLoadEnumDesc(t reflect.Type) pref.EnumDescriptor { func LegacyLoadEnumDesc(t reflect.Type) protoreflect.EnumDescriptor {
// Fast-path: check if an EnumDescriptor is cached for this concrete type. // Fast-path: check if an EnumDescriptor is cached for this concrete type.
if ed, ok := legacyEnumDescCache.Load(t); ok { if ed, ok := legacyEnumDescCache.Load(t); ok {
return ed.(pref.EnumDescriptor) return ed.(protoreflect.EnumDescriptor)
} }
// Slow-path: initialize EnumDescriptor from the raw descriptor. // Slow-path: initialize EnumDescriptor from the raw descriptor.
ev := reflect.Zero(t).Interface() ev := reflect.Zero(t).Interface()
if _, ok := ev.(pref.Enum); ok { if _, ok := ev.(protoreflect.Enum); ok {
panic(fmt.Sprintf("%v already implements proto.Enum", t)) panic(fmt.Sprintf("%v already implements proto.Enum", t))
} }
edV1, ok := ev.(enumV1) edV1, ok := ev.(enumV1)
@@ -132,7 +131,7 @@ func LegacyLoadEnumDesc(t reflect.Type) pref.EnumDescriptor {
} }
b, idxs := edV1.EnumDescriptor() b, idxs := edV1.EnumDescriptor()
var ed pref.EnumDescriptor var ed protoreflect.EnumDescriptor
if len(idxs) == 1 { if len(idxs) == 1 {
ed = legacyLoadFileDesc(b).Enums().Get(idxs[0]) ed = legacyLoadFileDesc(b).Enums().Get(idxs[0])
} else { } else {
@@ -158,10 +157,10 @@ var aberrantEnumDescCache sync.Map // map[reflect.Type]protoreflect.EnumDescript
// We are unable to use the global enum registry since it is // We are unable to use the global enum registry since it is
// unfortunately keyed by the protobuf full name, which we also do not know. // unfortunately keyed by the protobuf full name, which we also do not know.
// Thus, this produces some bogus enum descriptor based on the Go type name. // Thus, this produces some bogus enum descriptor based on the Go type name.
func aberrantLoadEnumDesc(t reflect.Type) pref.EnumDescriptor { func aberrantLoadEnumDesc(t reflect.Type) protoreflect.EnumDescriptor {
// Fast-path: check if an EnumDescriptor is cached for this concrete type. // Fast-path: check if an EnumDescriptor is cached for this concrete type.
if ed, ok := aberrantEnumDescCache.Load(t); ok { if ed, ok := aberrantEnumDescCache.Load(t); ok {
return ed.(pref.EnumDescriptor) return ed.(protoreflect.EnumDescriptor)
} }
// Slow-path: construct a bogus, but unique EnumDescriptor. // Slow-path: construct a bogus, but unique EnumDescriptor.
@@ -182,7 +181,7 @@ func aberrantLoadEnumDesc(t reflect.Type) pref.EnumDescriptor {
// An exhaustive query is clearly impractical, but can be best-effort. // An exhaustive query is clearly impractical, but can be best-effort.
if ed, ok := aberrantEnumDescCache.LoadOrStore(t, ed); ok { if ed, ok := aberrantEnumDescCache.LoadOrStore(t, ed); ok {
return ed.(pref.EnumDescriptor) return ed.(protoreflect.EnumDescriptor)
} }
return ed return ed
} }
@@ -192,7 +191,7 @@ func aberrantLoadEnumDesc(t reflect.Type) pref.EnumDescriptor {
// It should be sufficiently unique within a program. // It should be sufficiently unique within a program.
// //
// This is exported for testing purposes. // This is exported for testing purposes.
func AberrantDeriveFullName(t reflect.Type) pref.FullName { func AberrantDeriveFullName(t reflect.Type) protoreflect.FullName {
sanitize := func(r rune) rune { sanitize := func(r rune) rune {
switch { switch {
case r == '/': case r == '/':
@@ -215,5 +214,5 @@ func AberrantDeriveFullName(t reflect.Type) pref.FullName {
ss[i] = "x" + s ss[i] = "x" + s
} }
} }
return pref.FullName(strings.Join(ss, ".")) return protoreflect.FullName(strings.Join(ss, "."))
} }

View File

@@ -12,21 +12,21 @@ import (
"reflect" "reflect"
"google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/internal/errors"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
// These functions exist to support exported APIs in generated protobufs. // These functions exist to support exported APIs in generated protobufs.
// While these are deprecated, they cannot be removed for compatibility reasons. // While these are deprecated, they cannot be removed for compatibility reasons.
// LegacyEnumName returns the name of enums used in legacy code. // LegacyEnumName returns the name of enums used in legacy code.
func (Export) LegacyEnumName(ed pref.EnumDescriptor) string { func (Export) LegacyEnumName(ed protoreflect.EnumDescriptor) string {
return legacyEnumName(ed) return legacyEnumName(ed)
} }
// LegacyMessageTypeOf returns the protoreflect.MessageType for m, // LegacyMessageTypeOf returns the protoreflect.MessageType for m,
// with name used as the message name if necessary. // with name used as the message name if necessary.
func (Export) LegacyMessageTypeOf(m piface.MessageV1, name pref.FullName) pref.MessageType { func (Export) LegacyMessageTypeOf(m protoiface.MessageV1, name protoreflect.FullName) protoreflect.MessageType {
if mv := (Export{}).protoMessageV2Of(m); mv != nil { if mv := (Export{}).protoMessageV2Of(m); mv != nil {
return mv.ProtoReflect().Type() return mv.ProtoReflect().Type()
} }
@@ -36,9 +36,9 @@ func (Export) LegacyMessageTypeOf(m piface.MessageV1, name pref.FullName) pref.M
// UnmarshalJSONEnum unmarshals an enum from a JSON-encoded input. // UnmarshalJSONEnum unmarshals an enum from a JSON-encoded input.
// The input can either be a string representing the enum value by name, // The input can either be a string representing the enum value by name,
// or a number representing the enum number itself. // or a number representing the enum number itself.
func (Export) UnmarshalJSONEnum(ed pref.EnumDescriptor, b []byte) (pref.EnumNumber, error) { func (Export) UnmarshalJSONEnum(ed protoreflect.EnumDescriptor, b []byte) (protoreflect.EnumNumber, error) {
if b[0] == '"' { if b[0] == '"' {
var name pref.Name var name protoreflect.Name
if err := json.Unmarshal(b, &name); err != nil { if err := json.Unmarshal(b, &name); err != nil {
return 0, errors.New("invalid input for enum %v: %s", ed.FullName(), b) return 0, errors.New("invalid input for enum %v: %s", ed.FullName(), b)
} }
@@ -48,7 +48,7 @@ func (Export) UnmarshalJSONEnum(ed pref.EnumDescriptor, b []byte) (pref.EnumNumb
} }
return ev.Number(), nil return ev.Number(), nil
} else { } else {
var num pref.EnumNumber var num protoreflect.EnumNumber
if err := json.Unmarshal(b, &num); err != nil { if err := json.Unmarshal(b, &num); err != nil {
return 0, errors.New("invalid input for enum %v: %s", ed.FullName(), b) return 0, errors.New("invalid input for enum %v: %s", ed.FullName(), b)
} }
@@ -81,8 +81,8 @@ func (Export) CompressGZIP(in []byte) (out []byte) {
blockHeader[0] = 0x01 // final bit per RFC 1951, section 3.2.3. blockHeader[0] = 0x01 // final bit per RFC 1951, section 3.2.3.
blockSize = len(in) blockSize = len(in)
} }
binary.LittleEndian.PutUint16(blockHeader[1:3], uint16(blockSize)^0x0000) binary.LittleEndian.PutUint16(blockHeader[1:3], uint16(blockSize))
binary.LittleEndian.PutUint16(blockHeader[3:5], uint16(blockSize)^0xffff) binary.LittleEndian.PutUint16(blockHeader[3:5], ^uint16(blockSize))
out = append(out, blockHeader[:]...) out = append(out, blockHeader[:]...)
out = append(out, in[:blockSize]...) out = append(out, in[:blockSize]...)
in = in[blockSize:] in = in[blockSize:]

View File

@@ -12,16 +12,16 @@ import (
ptag "google.golang.org/protobuf/internal/encoding/tag" ptag "google.golang.org/protobuf/internal/encoding/tag"
"google.golang.org/protobuf/internal/filedesc" "google.golang.org/protobuf/internal/filedesc"
"google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/pragma"
pref "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
preg "google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/reflect/protoregistry"
piface "google.golang.org/protobuf/runtime/protoiface" "google.golang.org/protobuf/runtime/protoiface"
) )
func (xi *ExtensionInfo) initToLegacy() { func (xi *ExtensionInfo) initToLegacy() {
xd := xi.desc xd := xi.desc
var parent piface.MessageV1 var parent protoiface.MessageV1
messageName := xd.ContainingMessage().FullName() messageName := xd.ContainingMessage().FullName()
if mt, _ := preg.GlobalTypes.FindMessageByName(messageName); mt != nil { if mt, _ := protoregistry.GlobalTypes.FindMessageByName(messageName); mt != nil {
// Create a new parent message and unwrap it if possible. // Create a new parent message and unwrap it if possible.
mv := mt.New().Interface() mv := mt.New().Interface()
t := reflect.TypeOf(mv) t := reflect.TypeOf(mv)
@@ -31,7 +31,7 @@ func (xi *ExtensionInfo) initToLegacy() {
// Check whether the message implements the legacy v1 Message interface. // Check whether the message implements the legacy v1 Message interface.
mz := reflect.Zero(t).Interface() mz := reflect.Zero(t).Interface()
if mz, ok := mz.(piface.MessageV1); ok { if mz, ok := mz.(protoiface.MessageV1); ok {
parent = mz parent = mz
} }
} }
@@ -46,7 +46,7 @@ func (xi *ExtensionInfo) initToLegacy() {
// Reconstruct the legacy enum full name. // Reconstruct the legacy enum full name.
var enumName string var enumName string
if xd.Kind() == pref.EnumKind { if xd.Kind() == protoreflect.EnumKind {
enumName = legacyEnumName(xd.Enum()) enumName = legacyEnumName(xd.Enum())
} }
@@ -77,16 +77,16 @@ func (xi *ExtensionInfo) initFromLegacy() {
// field number is specified. In such a case, use a placeholder. // field number is specified. In such a case, use a placeholder.
if xi.ExtendedType == nil || xi.ExtensionType == nil { if xi.ExtendedType == nil || xi.ExtensionType == nil {
xd := placeholderExtension{ xd := placeholderExtension{
name: pref.FullName(xi.Name), name: protoreflect.FullName(xi.Name),
number: pref.FieldNumber(xi.Field), number: protoreflect.FieldNumber(xi.Field),
} }
xi.desc = extensionTypeDescriptor{xd, xi} xi.desc = extensionTypeDescriptor{xd, xi}
return return
} }
// Resolve enum or message dependencies. // Resolve enum or message dependencies.
var ed pref.EnumDescriptor var ed protoreflect.EnumDescriptor
var md pref.MessageDescriptor var md protoreflect.MessageDescriptor
t := reflect.TypeOf(xi.ExtensionType) t := reflect.TypeOf(xi.ExtensionType)
isOptional := t.Kind() == reflect.Ptr && t.Elem().Kind() != reflect.Struct isOptional := t.Kind() == reflect.Ptr && t.Elem().Kind() != reflect.Struct
isRepeated := t.Kind() == reflect.Slice && t.Elem().Kind() != reflect.Uint8 isRepeated := t.Kind() == reflect.Slice && t.Elem().Kind() != reflect.Uint8
@@ -94,18 +94,18 @@ func (xi *ExtensionInfo) initFromLegacy() {
t = t.Elem() t = t.Elem()
} }
switch v := reflect.Zero(t).Interface().(type) { switch v := reflect.Zero(t).Interface().(type) {
case pref.Enum: case protoreflect.Enum:
ed = v.Descriptor() ed = v.Descriptor()
case enumV1: case enumV1:
ed = LegacyLoadEnumDesc(t) ed = LegacyLoadEnumDesc(t)
case pref.ProtoMessage: case protoreflect.ProtoMessage:
md = v.ProtoReflect().Descriptor() md = v.ProtoReflect().Descriptor()
case messageV1: case messageV1:
md = LegacyLoadMessageDesc(t) md = LegacyLoadMessageDesc(t)
} }
// Derive basic field information from the struct tag. // Derive basic field information from the struct tag.
var evs pref.EnumValueDescriptors var evs protoreflect.EnumValueDescriptors
if ed != nil { if ed != nil {
evs = ed.Values() evs = ed.Values()
} }
@@ -114,8 +114,8 @@ func (xi *ExtensionInfo) initFromLegacy() {
// Construct a v2 ExtensionType. // Construct a v2 ExtensionType.
xd := &filedesc.Extension{L2: new(filedesc.ExtensionL2)} xd := &filedesc.Extension{L2: new(filedesc.ExtensionL2)}
xd.L0.ParentFile = filedesc.SurrogateProto2 xd.L0.ParentFile = filedesc.SurrogateProto2
xd.L0.FullName = pref.FullName(xi.Name) xd.L0.FullName = protoreflect.FullName(xi.Name)
xd.L1.Number = pref.FieldNumber(xi.Field) xd.L1.Number = protoreflect.FieldNumber(xi.Field)
xd.L1.Cardinality = fd.L1.Cardinality xd.L1.Cardinality = fd.L1.Cardinality
xd.L1.Kind = fd.L1.Kind xd.L1.Kind = fd.L1.Kind
xd.L2.IsPacked = fd.L1.IsPacked xd.L2.IsPacked = fd.L1.IsPacked
@@ -138,21 +138,21 @@ func (xi *ExtensionInfo) initFromLegacy() {
} }
type placeholderExtension struct { type placeholderExtension struct {
name pref.FullName name protoreflect.FullName
number pref.FieldNumber number protoreflect.FieldNumber
} }
func (x placeholderExtension) ParentFile() pref.FileDescriptor { return nil } func (x placeholderExtension) ParentFile() protoreflect.FileDescriptor { return nil }
func (x placeholderExtension) Parent() pref.Descriptor { return nil } func (x placeholderExtension) Parent() protoreflect.Descriptor { return nil }
func (x placeholderExtension) Index() int { return 0 } func (x placeholderExtension) Index() int { return 0 }
func (x placeholderExtension) Syntax() pref.Syntax { return 0 } func (x placeholderExtension) Syntax() protoreflect.Syntax { return 0 }
func (x placeholderExtension) Name() pref.Name { return x.name.Name() } func (x placeholderExtension) Name() protoreflect.Name { return x.name.Name() }
func (x placeholderExtension) FullName() pref.FullName { return x.name } func (x placeholderExtension) FullName() protoreflect.FullName { return x.name }
func (x placeholderExtension) IsPlaceholder() bool { return true } func (x placeholderExtension) IsPlaceholder() bool { return true }
func (x placeholderExtension) Options() pref.ProtoMessage { return descopts.Field } func (x placeholderExtension) Options() protoreflect.ProtoMessage { return descopts.Field }
func (x placeholderExtension) Number() pref.FieldNumber { return x.number } func (x placeholderExtension) Number() protoreflect.FieldNumber { return x.number }
func (x placeholderExtension) Cardinality() pref.Cardinality { return 0 } func (x placeholderExtension) Cardinality() protoreflect.Cardinality { return 0 }
func (x placeholderExtension) Kind() pref.Kind { return 0 } func (x placeholderExtension) Kind() protoreflect.Kind { return 0 }
func (x placeholderExtension) HasJSONName() bool { return false } func (x placeholderExtension) HasJSONName() bool { return false }
func (x placeholderExtension) JSONName() string { return "[" + string(x.name) + "]" } func (x placeholderExtension) JSONName() string { return "[" + string(x.name) + "]" }
func (x placeholderExtension) TextName() string { return "[" + string(x.name) + "]" } func (x placeholderExtension) TextName() string { return "[" + string(x.name) + "]" }
@@ -163,14 +163,14 @@ func (x placeholderExtension) IsWeak() bool { retu
func (x placeholderExtension) IsPacked() bool { return false } func (x placeholderExtension) IsPacked() bool { return false }
func (x placeholderExtension) IsList() bool { return false } func (x placeholderExtension) IsList() bool { return false }
func (x placeholderExtension) IsMap() bool { return false } func (x placeholderExtension) IsMap() bool { return false }
func (x placeholderExtension) MapKey() pref.FieldDescriptor { return nil } func (x placeholderExtension) MapKey() protoreflect.FieldDescriptor { return nil }
func (x placeholderExtension) MapValue() pref.FieldDescriptor { return nil } func (x placeholderExtension) MapValue() protoreflect.FieldDescriptor { return nil }
func (x placeholderExtension) HasDefault() bool { return false } func (x placeholderExtension) HasDefault() bool { return false }
func (x placeholderExtension) Default() pref.Value { return pref.Value{} } func (x placeholderExtension) Default() protoreflect.Value { return protoreflect.Value{} }
func (x placeholderExtension) DefaultEnumValue() pref.EnumValueDescriptor { return nil } func (x placeholderExtension) DefaultEnumValue() protoreflect.EnumValueDescriptor { return nil }
func (x placeholderExtension) ContainingOneof() pref.OneofDescriptor { return nil } func (x placeholderExtension) ContainingOneof() protoreflect.OneofDescriptor { return nil }
func (x placeholderExtension) ContainingMessage() pref.MessageDescriptor { return nil } func (x placeholderExtension) ContainingMessage() protoreflect.MessageDescriptor { return nil }
func (x placeholderExtension) Enum() pref.EnumDescriptor { return nil } func (x placeholderExtension) Enum() protoreflect.EnumDescriptor { return nil }
func (x placeholderExtension) Message() pref.MessageDescriptor { return nil } func (x placeholderExtension) Message() protoreflect.MessageDescriptor { return nil }
func (x placeholderExtension) ProtoType(pref.FieldDescriptor) { return } func (x placeholderExtension) ProtoType(protoreflect.FieldDescriptor) { return }
func (x placeholderExtension) ProtoInternal(pragma.DoNotImplement) { return } func (x placeholderExtension) ProtoInternal(pragma.DoNotImplement) { return }

Some files were not shown because too many files have changed in this diff Show More