Skip to content

Commit

Permalink
Merge "[FAB-3011] Fix max enrollment checking logic"
Browse files Browse the repository at this point in the history
  • Loading branch information
christo4ferris authored and Gerrit Code Review committed Jun 2, 2017
2 parents e4e0a0d + 120b139 commit 400f699
Show file tree
Hide file tree
Showing 23 changed files with 490 additions and 147 deletions.
2 changes: 1 addition & 1 deletion api/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ type RegistrationRequest struct {
Secret string `json:"secret,omitempty" help:"The enrollment secret for the identity being registered"`
// MaxEnrollments is the maximum number of times the secret can
// be reused to enroll.
MaxEnrollments int `json:"max_enrollments,omitempty" help:"The maximum number of times the secret can be reused to enroll."`
MaxEnrollments int `json:"max_enrollments,omitempty" def:"-1" help:"The maximum number of times the secret can be reused to enroll."`
// is returned in the response.
// The identity's affiliation.
// For example, an affiliation of "org1.department1" associates the identity with "department1" in "org1".
Expand Down
1 change: 1 addition & 0 deletions cmd/fabric-ca-client/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,7 @@ id:
type:
maxenrollments:
affiliation:
maxenrollments: -1
attributes:
- name:
value:
Expand Down
37 changes: 17 additions & 20 deletions cmd/fabric-ca-client/main_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,11 @@ const jsonConfig = `{
}
}`

const (
serverPort = 7054
testdataDir = "homeDir"
)

var (
defYaml string
fabricCADB = path.Join(tdDir, db)
Expand Down Expand Up @@ -163,7 +168,7 @@ func TestCreateDefaultConfigFile(t *testing.T) {
func TestClientCommandsNoTLS(t *testing.T) {
os.Remove(fabricCADB)

srv = getServer()
srv = lib.TestGetServer(serverPort, testdataDir, "", -1, t)
srv.HomeDir = tdDir
srv.Config.Debug = true

Expand Down Expand Up @@ -488,7 +493,6 @@ func testRevoke(t *testing.T) {
err = RunMain([]string{cmdName, "revoke", "-u", "http://localhost:7054", "--revoke.name", "testRegister4", "--revoke.serial", "", "--revoke.aki", ""})
if err != nil {
t.Errorf("User with root affiliation failed to revoke, error: %s", err)

}

os.Remove(defYaml) // Delete default config file
Expand Down Expand Up @@ -594,10 +598,10 @@ func TestGetCACert(t *testing.T) {
func TestClientCommandsUsingConfigFile(t *testing.T) {
os.Remove(fabricCADB)

srv = getServer()
srv = lib.TestGetServer(serverPort, testdataDir, "", -1, t)
srv.Config.Debug = true

err := srv.RegisterBootstrapUser("admin", "adminpw", "bank1")
err := srv.RegisterBootstrapUser("admin", "adminpw", "org1")
if err != nil {
t.Errorf("Failed to register bootstrap user: %s", err)
}
Expand Down Expand Up @@ -626,15 +630,10 @@ func TestClientCommandsUsingConfigFile(t *testing.T) {
func TestClientCommandsTLSEnvVar(t *testing.T) {
os.Remove(fabricCADB)

srv = getServer()
srv = lib.TestGetServer(serverPort, testdataDir, "", -1, t)
srv.Config.Debug = true

err := srv.RegisterBootstrapUser("admin", "adminpw", "bank1")
if err != nil {
t.Errorf("Failed to register bootstrap user: %s", err)
}

err = srv.RegisterBootstrapUser("admin2", "adminpw2", "bank1")
err := srv.RegisterBootstrapUser("admin2", "adminpw2", "org1")
if err != nil {
t.Errorf("Failed to register bootstrap user: %s", err)
}
Expand Down Expand Up @@ -671,15 +670,10 @@ func TestClientCommandsTLSEnvVar(t *testing.T) {
func TestClientCommandsTLS(t *testing.T) {
os.Remove(fabricCADB)

srv = getServer()
srv = lib.TestGetServer(serverPort, testdataDir, "", -1, t)
srv.Config.Debug = true

err := srv.RegisterBootstrapUser("admin", "adminpw", "bank1")
if err != nil {
t.Errorf("Failed to register bootstrap user: %s", err)
}

err = srv.RegisterBootstrapUser("admin2", "adminpw2", "bank1")
err := srv.RegisterBootstrapUser("admin2", "adminpw2", "org1")
if err != nil {
t.Errorf("Failed to register bootstrap user: %s", err)
}
Expand Down Expand Up @@ -713,7 +707,7 @@ func TestClientCommandsTLS(t *testing.T) {
func TestMultiCA(t *testing.T) {
cleanMultiCADir()

srv = getServer()
srv = lib.TestGetServer(serverPort, testdataDir, "", -1, t)
srv.HomeDir = "../../testdata"
srv.Config.CAfiles = []string{"ca/rootca/ca1/fabric-ca-server-config.yaml", "ca/rootca/ca2/fabric-ca-server-config.yaml"}
srv.CA.Config.CSR.Hosts = []string{"hostname"}
Expand Down Expand Up @@ -746,7 +740,7 @@ func TestMultiCA(t *testing.T) {
t.Errorf("client enroll -c -u failed: %s", err)
}

err = RunMain([]string{cmdName, "register", "-c", testYaml, "-d", "--id.name", "testuser", "--id.type", "user", "--id.affiliation", "org1", "--caname", "rootca1"})
err = RunMain([]string{cmdName, "register", "-c", testYaml, "-d", "--id.name", "testuser", "--id.type", "user", "--id.affiliation", "org2", "--caname", "rootca1"})
if err != nil {
t.Errorf("client enroll -c -u failed: %s", err)
}
Expand Down Expand Up @@ -922,6 +916,9 @@ func startServer(home string, port int, t *testing.T) *lib.Server {
CA: lib.CA{
Config: &lib.CAConfig{
Affiliations: affiliations,
Registry: lib.CAConfigRegistry{
MaxEnrollments: -1,
},
},
},
}
Expand Down
6 changes: 3 additions & 3 deletions cmd/fabric-ca-server/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -140,15 +140,16 @@ ca:
#############################################################################
registry:
# Maximum number of times a password/secret can be reused for enrollment
# (default: 0, which means there is no limit)
maxEnrollments: 0
# (default: -1, which means there is no limit)
maxenrollments: -1
# Contains identity information which is used when LDAP is disabled
identities:
- name: <<<ADMIN>>>
pass: <<<ADMINPW>>>
type: client
affiliation: ""
maxenrollments: -1
attrs:
hf.Registrar.Roles: "client,user,peer,validator,auditor,ca"
hf.Registrar.DelegateRoles: "client,user,validator,auditor"
Expand Down Expand Up @@ -374,7 +375,6 @@ func configInit() (err error) {
}

// Read the config
// viper.SetConfigFile(cfgFileName)
viper.AutomaticEnv() // read in environment variables that match
err = lib.UnmarshalConfig(serverCfg, viper.GetViper(), cfgFileName, true, true)
if err != nil {
Expand Down
19 changes: 14 additions & 5 deletions docs/source/users-guide.rst
Original file line number Diff line number Diff line change
Expand Up @@ -322,8 +322,8 @@ the server's home directory (see `Fabric CA Server <#server>`__ section more inf
#############################################################################
registry:
# Maximum number of times a password/secret can be reused for enrollment
# (default: 0, which means there is no limit)
maxEnrollments: 0
# (default: -1, which means there is no limit)
maxenrollments: -1

# Contains identity information which is used when LDAP is disabled
identities:
Expand Down Expand Up @@ -810,12 +810,14 @@ To cause the Fabric CA server to listen on ``https`` rather than
``http``, set ``tls.enabled`` to ``true``.

To limit the number of times that the same secret (or password) can be
used for enrollment, set the ``registry.maxEnrollments`` in the configuration
used for enrollment, set the ``registry.maxenrollments`` in the configuration
file to the appropriate value. If you set the value to 1, the Fabric CA
server allows passwords to only be used once for a particular enrollment
ID. If you set the value to 0, the Fabric CA server places no limit on
ID. If you set the value to -1, the Fabric CA server places no limit on
the number of times that a secret can be reused for enrollment. The
default value is 0.
default value is -1. Setting the value to 0, the Fabric CA server will
disable enrollment for all identitiies and registeration of identities will
not be allowed.

The Fabric CA server should now be listening on port 7054.

Expand Down Expand Up @@ -1242,6 +1244,7 @@ file contains the following:
name:
type: user
affiliation: org1.department1
maxenrollments: -1
attributes:
- name: hf.Revoker
value: true
Expand All @@ -1261,6 +1264,12 @@ and two attributes: "hf.Revoker" and "anotherAttrName".
To register an identity with multiple attributes requires specifying all attribute names and values
in the configuration file as shown above.

Setting `maxenrollments` to 0 or leaving it out from the configuration will result in the identity
being registerd to use the CA's max enrollment value. Furthermore, the max enrollment value for
an identity being registered cannot exceed the CA's max enrollment value. For example, if the CA's
max enrollment value is 5. Any new identity must have a value less than or equal to 5, and also
can't set it to -1 (infinite enrollments).

Next, let's register a peer identity which will be used to enroll the peer in the following section.
The following command registers the **peer1** identity. Note that we choose to specify our own
password (or secret) rather than letting the server generate one for us.
Expand Down
8 changes: 5 additions & 3 deletions lib/ca.go
Original file line number Diff line number Diff line change
Expand Up @@ -187,7 +187,7 @@ func (ca *CA) initKeyMaterial(renew bool) error {
log.Info("The CA key and certificate files already exist")
log.Infof("Key file location: %s", keyFile)
log.Infof("Certificate file location: %s", certFile)
err := ca.validateCert(certFile, keyFile)
err = ca.validateCert(certFile, keyFile)
if err != nil {
return fmt.Errorf("Validation of certificate and key failed: %s", err)
}
Expand Down Expand Up @@ -369,6 +369,7 @@ func (ca *CA) initConfig() (err error) {
// Init config if not set
if ca.Config == nil {
ca.Config = new(CAConfig)
ca.Config.Registry.MaxEnrollments = -1
}
// Set config defaults
cfg := ca.Config
Expand Down Expand Up @@ -615,17 +616,18 @@ func (ca *CA) addIdentity(id *CAConfigIdentity, errIfFound bool) error {
return nil
}

maxEnrollments, err := ca.getMaxEnrollments(id.MaxEnrollments)
id.MaxEnrollments, err = getMaxEnrollments(id.MaxEnrollments, ca.Config.Registry.MaxEnrollments)
if err != nil {
return err
}

rec := spi.UserInfo{
Name: id.Name,
Pass: id.Pass,
Type: id.Type,
Affiliation: id.Affiliation,
Attributes: ca.convertAttrs(id.Attrs),
MaxEnrollments: maxEnrollments,
MaxEnrollments: id.MaxEnrollments,
}
err = ca.registry.InsertUser(rec)
if err != nil {
Expand Down
2 changes: 1 addition & 1 deletion lib/caconfig.go
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@ type CAConfigDB struct {

// CAConfigRegistry is the registry part of the server's config
type CAConfigRegistry struct {
MaxEnrollments int `def:"0" help:"Maximum number of enrollments; valid if LDAP not enabled"`
MaxEnrollments int `def:"-1" help:"Maximum number of enrollments; valid if LDAP not enabled"`
Identities []CAConfigIdentity
}

Expand Down
5 changes: 2 additions & 3 deletions lib/client_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,8 +48,7 @@ const (
)

func TestClient(t *testing.T) {

server := getServer(ctport1, path.Join(serversDir, "c1"), "", 1, t)
server := TestGetServer(ctport1, path.Join(serversDir, "c1"), "", 1, t)
if server == nil {
return
}
Expand Down Expand Up @@ -276,7 +275,7 @@ func testLoadBadCSRInfo(c *Client, t *testing.T) {
func TestCustomizableMaxEnroll(t *testing.T) {
os.Remove("../testdata/fabric-ca-server.db")

srv := getServer(ctport2, path.Join(serversDir, "c2"), "", 3, t)
srv := TestGetServer(ctport2, path.Join(serversDir, "c2"), "", 3, t)
if srv == nil {
return
}
Expand Down
10 changes: 4 additions & 6 deletions lib/client_whitebox_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,10 @@ import (
)

const (
whitePort = 7058
rootDir = "rootDir"
testdataDir = "../testdata"
user = "admin"
pass = "adminpw"
serversDir = "testservers"
whitePort = 7058
user = "admin"
pass = "adminpw"
serversDir = "testservers"
)

var clientConfig = path.Join(testdataDir, "client-config.json")
Expand Down
13 changes: 7 additions & 6 deletions lib/dasqlite_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -157,10 +157,11 @@ func testUpdateUser(ta TestAccessor, t *testing.T) {
ta.Truncate()

insert := spi.UserInfo{
Name: "testId",
Pass: "123456",
Type: "client",
Attributes: []api.Attribute{},
Name: "testId",
Pass: "123456",
Type: "client",
Attributes: []api.Attribute{},
MaxEnrollments: 1,
}

err := ta.Accessor.InsertUser(insert)
Expand All @@ -180,9 +181,9 @@ func testUpdateUser(ta TestAccessor, t *testing.T) {
t.Errorf("Error occured during querying of ID: %s, error: %s", insert.Name, err)
}

err = user.Login(insert.Pass)
err = user.Login(insert.Pass, -1)
if err != nil {
t.Error("Failed to update user's password")
t.Error("Failed to login in user: ", err)
}

}
Expand Down

0 comments on commit 400f699

Please sign in to comment.