Skip to content
This repository has been archived by the owner on Jun 27, 2023. It is now read-only.

Can't mock internal interfaces #29

Closed
ralfthewise opened this issue Mar 23, 2016 · 5 comments · Fixed by #169
Closed

Can't mock internal interfaces #29

ralfthewise opened this issue Mar 23, 2016 · 5 comments · Fixed by #169

Comments

@ralfthewise
Copy link

I get the following:

$ mockgen -self_package users -package users -destination ./cmd/api/internal/users/mocks_users_test.go github.com/foobar/api/cmd/api/internal/users Client
package main
    imports github.com/foobar/api/cmd/api/internal/users: use of internal package not allowed
2016/03/23 13:51:08 Loading input failed: exit status 1
@ralfthewise
Copy link
Author

Is somewhat related to #4. If the PR for that issue were tweaked to create the temp dir in the same folder as the destination file, I think it would actually fix this issue as well. Until it is fixed, you can workaround it with the following bash script (I use it on linux, haven't tested on OSX):

#!/bin/bash

if [ $# -ne 4 ] ; then
  echo "Usage: $0 <destination package> <destination file> <mocked package> <mocked interfaces>"
  echo "  ex: $0 users ./cmd/api/internal/users/mocks_api_test.go github.com/foobar/api Client,UsersService"
  exit 0
fi

DEST_PACKAGE="$1" && shift 1
DEST_FILE="$1" && shift 1
MOCKED_PACKAGE="$1" && shift 1
MOCKED_INTERFACES="$1" && shift 1

PARENT_DIR=$(dirname "$DEST_FILE")
mkdir -p "$PARENT_DIR"
TEMP_DIR=$(TMPDIR="$PARENT_DIR" mktemp --directory)
echo Created "$TEMP_DIR"

mockgen -prog_only $MOCKED_PACKAGE $MOCKED_INTERFACES > "${TEMP_DIR}/main.go"
go build -o "${TEMP_DIR}/main" "${TEMP_DIR}/main.go"
mockgen -self_package $DEST_PACKAGE -package $DEST_PACKAGE -destination "$DEST_FILE" -exec_only "${TEMP_DIR}/main" $MOCKED_PACKAGE $MOCKED_INTERFACES

rm -rf "$TEMP_DIR"

@dsymonds
Copy link
Contributor

This seems like the same issue as mocking unexported interfaces. If it's an internal interface, you should either make the mock equally internal, or expose the interface. Who's going to be using the interface otherwise? Mock packages should be nearby the thing they are generated from.

@ralfthewise
Copy link
Author

I am attempting to make the mock equally internal (I'm creating the mock as part of the same package that contains the interfaces being mocked), the problem is that mockgen creates a temporary file outside of the internal tree to do the reflection and as such it can't import the internal package. The sequence of events is as follows:

  1. mockgen is run targeting an interface of internal package github.com/foobar/cmd/internal/pkg
  2. mockgen creates its reflection file at /tmp/gomock_reflect_5nVGGRQmT8/prog.go
  3. mockgen tries to compile the above file
  4. compilation fails because the prog.go file is trying to import the internal package github.com/foobar/cmd/internal/pkg

@ralfthewise
Copy link
Author

I should note that it may have been go1.5 that enforced the internal mechanism, updating the title.

@ralfthewise ralfthewise changed the title Can't mock internal interfaces with go1.6 Can't mock internal interfaces Mar 24, 2016
@wichert
Copy link

wichert commented May 10, 2022

FYI I am still seeing this with mockgen 1.6.0:

$ mockgen -version                                                                                                             
v1.6.0

$ mockgen  -package=mockndsmodel -destination=mock/mock.go . Service,RoutingService,SmartLayerTileService                      
package command-line-arguments
	prog.go:14:2: use of internal package github.internal.domain/org/amp/nds/internal/model not allowed

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants