Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

LOOPP plugin config validation service #12430

Merged
Merged
Show file tree
Hide file tree
Changes from 14 commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
370cf7c
Initial draft
george-dorin Mar 11, 2024
2730170
Initial draft
george-dorin Mar 14, 2024
61f6562
Update go mod
george-dorin Mar 19, 2024
9d7eeb5
Fix go sum
george-dorin Mar 19, 2024
031d295
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Mar 19, 2024
1819331
Pin to chainlink-common PR
george-dorin Mar 19, 2024
145c9cd
Add tests
george-dorin Mar 20, 2024
6609376
Add unregister
george-dorin Mar 20, 2024
99636e2
Fix lint
george-dorin Mar 20, 2024
d2a8653
Implement feedback
george-dorin Mar 22, 2024
073e0e4
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Mar 22, 2024
ce0948d
Pin to latest version of chainlink-common PR
george-dorin Mar 22, 2024
4a6d842
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Mar 27, 2024
2bda63e
Pin to latest version of chainlink-common PR
george-dorin Mar 27, 2024
9f33f43
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Mar 28, 2024
3e80f35
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Mar 28, 2024
72a9bfc
Pin to latest version of chainlink-common PR
george-dorin Mar 28, 2024
2cfe4e4
Fix typo
george-dorin Mar 28, 2024
e8ef40b
Add comment for further work once BCF-3126 is implemented
george-dorin Apr 3, 2024
181fa93
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Apr 3, 2024
afe72c9
Pin to latest version of common PR
george-dorin Apr 3, 2024
b7cf21a
Merge branch 'develop' into chore/BCF-2777-reporting-plugin-LOOPP-job…
george-dorin Apr 4, 2024
db6d8c2
Bump to latest chainlink-common
george-dorin Apr 4, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions core/internal/features/ocr2/features_ocr2_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -437,7 +437,7 @@ typeABI = '''
'''
`
}
ocrJob, err := validate.ValidatedOracleSpecToml(apps[i].Config.OCR2(), apps[i].Config.Insecure(), fmt.Sprintf(`
ocrJob, err := validate.ValidatedOracleSpecToml(testutils.Context(t), apps[i].Config.OCR2(), apps[i].Config.Insecure(), fmt.Sprintf(`
type = "offchainreporting2"
relay = "evm"
schemaVersion = 1
Expand Down Expand Up @@ -488,7 +488,7 @@ juelsPerFeeCoinSource = """
answer1 [type=median index=0];
"""
juelsPerFeeCoinCacheDuration = "1m"
`, ocrContractAddress, kbs[i].ID(), transmitters[i], fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i, blockBeforeConfig.Number().Int64(), chainReaderSpec, fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i))
`, ocrContractAddress, kbs[i].ID(), transmitters[i], fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i, blockBeforeConfig.Number().Int64(), chainReaderSpec, fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i), nil)
require.NoError(t, err)
err = apps[i].AddJobV2(testutils.Context(t), &ocrJob)
require.NoError(t, err)
Expand Down Expand Up @@ -793,7 +793,7 @@ chainID = 1337
URL: models.WebURL(*u),
}))

ocrJob, err := validate.ValidatedOracleSpecToml(apps[i].Config.OCR2(), apps[i].Config.Insecure(), fmt.Sprintf(`
ocrJob, err := validate.ValidatedOracleSpecToml(testutils.Context(t), apps[i].Config.OCR2(), apps[i].Config.Insecure(), fmt.Sprintf(`
type = "offchainreporting2"
relay = "evm"
schemaVersion = 1
Expand Down Expand Up @@ -841,7 +841,7 @@ juelsPerFeeCoinSource = """
answer1 [type=median index=0];
"""
juelsPerFeeCoinCacheDuration = "1m"
`, ocrContractAddress, kbs[i].ID(), transmitters[i], fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i, fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i))
`, ocrContractAddress, kbs[i].ID(), transmitters[i], fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i, fmt.Sprintf("bridge%d", i), i, slowServers[i].URL, i), nil)
require.NoError(t, err)
err = apps[i].AddJobV2(testutils.Context(t), &ocrJob)
require.NoError(t, err)
Expand Down
20 changes: 20 additions & 0 deletions core/internal/mocks/application.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion core/scripts/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ require (
github.com/prometheus/client_golang v1.17.0
github.com/shopspring/decimal v1.3.1
github.com/smartcontractkit/chainlink-automation v1.0.2-0.20240311111125-22812a072c35
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240324144450-2bc22a6738ac
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240327143225-50583d49ed4e
github.com/smartcontractkit/chainlink-vrf v0.0.0-20231120191722-fef03814f868
github.com/smartcontractkit/chainlink/v2 v2.0.0-00010101000000-000000000000
github.com/smartcontractkit/libocr v0.0.0-20240326191951-2bbe9382d052
Expand Down
4 changes: 2 additions & 2 deletions core/scripts/go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -1187,8 +1187,8 @@ github.com/smartcontractkit/chain-selectors v1.0.10 h1:t9kJeE6B6G+hKD0GYR4kGJSCq
github.com/smartcontractkit/chain-selectors v1.0.10/go.mod h1:d4Hi+E1zqjy9HqMkjBE5q1vcG9VGgxf5VxiRHfzi2kE=
github.com/smartcontractkit/chainlink-automation v1.0.2-0.20240311111125-22812a072c35 h1:GNhRKD3izyzAoGMXDvVUAwEuzz4Atdj3U3RH7eak5Is=
github.com/smartcontractkit/chainlink-automation v1.0.2-0.20240311111125-22812a072c35/go.mod h1:2I0dWdYdK6jHPnSYYy7Y7Xp7L0YTnJ3KZtkhLQflsTU=
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240324144450-2bc22a6738ac h1:EjQDAPZu4N7s554uXzA7QOLZz+JnvjbBwSumExmzF0k=
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240324144450-2bc22a6738ac/go.mod h1://xWphjmC6GWJtT8l86J2VpnG21xNwFCb0thzz4ItEk=
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240327143225-50583d49ed4e h1:vrB84+Kjb2fQOwG/WDRNVNzvxc+qeJ+NUiEcjcCamvo=
github.com/smartcontractkit/chainlink-common v0.1.7-0.20240327143225-50583d49ed4e/go.mod h1:u2XnvJHl7sQ9HMlRnVLsOKgV9ihk0RGIYywB12p9gQQ=
github.com/smartcontractkit/chainlink-cosmos v0.4.1-0.20240213120401-01a23955f9f8 h1:I326nw5GwHQHsLKHwtu5Sb9EBLylC8CfUd7BFAS0jtg=
github.com/smartcontractkit/chainlink-cosmos v0.4.1-0.20240213120401-01a23955f9f8/go.mod h1:a65NtrK4xZb01mf0dDNghPkN2wXgcqFQ55ADthVBgMc=
github.com/smartcontractkit/chainlink-data-streams v0.0.0-20240220203239-09be0ea34540 h1:xFSv8561jsLtF6gYZr/zW2z5qUUAkcFkApin2mnbYTo=
Expand Down
15 changes: 13 additions & 2 deletions core/services/chainlink/application.go
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,7 @@ type Application interface {
GetExternalInitiatorManager() webhook.ExternalInitiatorManager
GetRelayers() RelayerChainInteroperators
GetLoopRegistry() *plugins.LoopRegistry
GetLoopRegistrarConfig() plugins.RegistrarConfig

// V2 Jobs (TOML specified)
JobSpawner() job.Spawner
Expand Down Expand Up @@ -149,6 +150,7 @@ type ChainlinkApplication struct {
secretGenerator SecretGenerator
profiler *pyroscope.Profiler
loopRegistry *plugins.LoopRegistry
loopRegistrarConfig plugins.RegistrarConfig

started bool
startStopMu sync.Mutex
Expand Down Expand Up @@ -424,10 +426,14 @@ func NewApplication(opts ApplicationOpts) (Application, error) {
} else {
globalLogger.Debug("Off-chain reporting disabled")
}

loopRegistrarConfig := plugins.NewRegistrarConfig(opts.GRPCOpts, opts.LoopRegistry.Register, opts.LoopRegistry.Unregister)

if cfg.OCR2().Enabled() {
globalLogger.Debug("Off-chain reporting v2 enabled")
registrarConfig := plugins.NewRegistrarConfig(opts.GRPCOpts, opts.LoopRegistry.Register)
ocr2DelegateConfig := ocr2.NewDelegateConfig(cfg.OCR2(), cfg.Mercury(), cfg.Threshold(), cfg.Insecure(), cfg.JobPipeline(), cfg.Database(), registrarConfig)

ocr2DelegateConfig := ocr2.NewDelegateConfig(cfg.OCR2(), cfg.Mercury(), cfg.Threshold(), cfg.Insecure(), cfg.JobPipeline(), cfg.Database(), loopRegistrarConfig)

delegates[job.OffchainReporting2] = ocr2.NewDelegate(
sqlxDB,
jobORM,
Expand Down Expand Up @@ -495,6 +501,7 @@ func NewApplication(opts ApplicationOpts) (Application, error) {
legacyEVMChains,
globalLogger,
opts.Version,
loopRegistrarConfig,
)
} else {
feedsService = &feeds.NullService{}
Expand Down Expand Up @@ -533,6 +540,7 @@ func NewApplication(opts ApplicationOpts) (Application, error) {
secretGenerator: opts.SecretGenerator,
profiler: profiler,
loopRegistry: loopRegistry,
loopRegistrarConfig: loopRegistrarConfig,

sqlxDB: opts.SqlxDB,
db: opts.DB,
Expand Down Expand Up @@ -603,6 +611,9 @@ func (app *ChainlinkApplication) StopIfStarted() error {
func (app *ChainlinkApplication) GetLoopRegistry() *plugins.LoopRegistry {
return app.loopRegistry
}
func (app *ChainlinkApplication) GetLoopRegistrarConfig() plugins.RegistrarConfig {
return app.loopRegistrarConfig
}

// Stop allows the application to exit by halting schedules, closing
// logs, and closing the DB connection.
Expand Down
80 changes: 42 additions & 38 deletions core/services/feeds/service.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ import (
"github.com/jmoiron/sqlx"

"github.com/smartcontractkit/chainlink-common/pkg/services"
"github.com/smartcontractkit/chainlink/v2/plugins"

"github.com/smartcontractkit/chainlink/v2/core/chains/evm/types"
"github.com/smartcontractkit/chainlink/v2/core/chains/evm/utils/big"
Expand Down Expand Up @@ -102,22 +103,23 @@ type Service interface {
type service struct {
services.StateMachine

orm ORM
jobORM job.ORM
q pg.Q
csaKeyStore keystore.CSA
p2pKeyStore keystore.P2P
ocr1KeyStore keystore.OCR
ocr2KeyStore keystore.OCR2
jobSpawner job.Spawner
insecureCfg InsecureConfig
jobCfg JobConfig
ocrCfg OCRConfig
ocr2cfg OCR2Config
connMgr ConnectionsManager
legacyChains legacyevm.LegacyChainContainer
lggr logger.Logger
version string
orm ORM
jobORM job.ORM
q pg.Q
csaKeyStore keystore.CSA
p2pKeyStore keystore.P2P
ocr1KeyStore keystore.OCR
ocr2KeyStore keystore.OCR2
jobSpawner job.Spawner
insecureCfg InsecureConfig
jobCfg JobConfig
ocrCfg OCRConfig
ocr2cfg OCR2Config
connMgr ConnectionsManager
legacyChains legacyevm.LegacyChainContainer
lggr logger.Logger
version string
loopRegistrarConfig plugins.RegistrarConfig
}

// NewService constructs a new feeds service
Expand All @@ -135,25 +137,27 @@ func NewService(
legacyChains legacyevm.LegacyChainContainer,
lggr logger.Logger,
version string,
rc plugins.RegistrarConfig,
) *service {
lggr = lggr.Named("Feeds")
svc := &service{
orm: orm,
jobORM: jobORM,
q: pg.NewQ(db, lggr, dbCfg),
jobSpawner: jobSpawner,
p2pKeyStore: keyStore.P2P(),
csaKeyStore: keyStore.CSA(),
ocr1KeyStore: keyStore.OCR(),
ocr2KeyStore: keyStore.OCR2(),
insecureCfg: insecureCfg,
jobCfg: jobCfg,
ocrCfg: ocrCfg,
ocr2cfg: ocr2Cfg,
connMgr: newConnectionsManager(lggr),
legacyChains: legacyChains,
lggr: lggr,
version: version,
orm: orm,
jobORM: jobORM,
q: pg.NewQ(db, lggr, dbCfg),
jobSpawner: jobSpawner,
p2pKeyStore: keyStore.P2P(),
csaKeyStore: keyStore.CSA(),
ocr1KeyStore: keyStore.OCR(),
ocr2KeyStore: keyStore.OCR2(),
insecureCfg: insecureCfg,
jobCfg: jobCfg,
ocrCfg: ocrCfg,
ocr2cfg: ocr2Cfg,
connMgr: newConnectionsManager(lggr),
legacyChains: legacyChains,
lggr: lggr,
version: version,
loopRegistrarConfig: rc,
}

return svc
Expand Down Expand Up @@ -534,7 +538,7 @@ type ProposeJobArgs struct {
// belonging to another feeds manager, we do not update it.
func (s *service) ProposeJob(ctx context.Context, args *ProposeJobArgs) (int64, error) {
// Validate the args
if err := s.validateProposeJobArgs(*args); err != nil {
if err := s.validateProposeJobArgs(ctx, *args); err != nil {
return 0, err
}

Expand Down Expand Up @@ -717,7 +721,7 @@ func (s *service) ApproveSpec(ctx context.Context, id int64, force bool) error {
return errors.Wrap(err, "fms rpc client")
}

j, err := s.generateJob(spec.Definition)
j, err := s.generateJob(ctx, spec.Definition)
if err != nil {
return errors.Wrap(err, "could not generate job from spec")
}
Expand Down Expand Up @@ -1121,7 +1125,7 @@ func (s *service) findExistingJobForOCRFlux(j *job.Job, qopts pg.QOpt) (int32, e
}

// generateJob validates and generates a job from a spec.
func (s *service) generateJob(spec string) (*job.Job, error) {
func (s *service) generateJob(ctx context.Context, spec string) (*job.Job, error) {
jobType, err := job.ValidateSpec(spec)
if err != nil {
return nil, errors.Wrap(err, "failed to parse job spec TOML")
Expand All @@ -1138,7 +1142,7 @@ func (s *service) generateJob(spec string) (*job.Job, error) {
if !s.ocr2cfg.Enabled() {
return nil, ErrOCR2Disabled
}
js, err = ocr2.ValidatedOracleSpecToml(s.ocr2cfg, s.insecureCfg, spec)
js, err = ocr2.ValidatedOracleSpecToml(ctx, s.ocr2cfg, s.insecureCfg, spec, s.loopRegistrarConfig)
case job.Bootstrap:
if !s.ocr2cfg.Enabled() {
return nil, ErrOCR2Disabled
Expand Down Expand Up @@ -1297,9 +1301,9 @@ func (s *service) newOCR2ConfigMsg(cfg OCR2ConfigModel) (*pb.OCR2Config, error)
return msg, nil
}

func (s *service) validateProposeJobArgs(args ProposeJobArgs) error {
func (s *service) validateProposeJobArgs(ctx context.Context, args ProposeJobArgs) error {
// Validate the job spec
j, err := s.generateJob(args.Spec)
j, err := s.generateJob(ctx, args.Spec)
if err != nil {
return errors.Wrap(err, "failed to generate a job based on spec")
}
Expand Down
2 changes: 1 addition & 1 deletion core/services/feeds/service_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -186,7 +186,7 @@ func setupTestServiceCfg(t *testing.T, overrideCfg func(c *chainlink.Config, s *
keyStore.On("P2P").Return(p2pKeystore)
keyStore.On("OCR").Return(ocr1Keystore)
keyStore.On("OCR2").Return(ocr2Keystore)
svc := feeds.NewService(orm, jobORM, db, spawner, keyStore, scopedConfig.Insecure(), scopedConfig.JobPipeline(), scopedConfig.OCR(), scopedConfig.OCR2(), scopedConfig.Database(), legacyChains, lggr, "1.0.0")
svc := feeds.NewService(orm, jobORM, db, spawner, keyStore, scopedConfig.Insecure(), scopedConfig.JobPipeline(), scopedConfig.OCR(), scopedConfig.OCR2(), scopedConfig.Database(), legacyChains, lggr, "1.0.0", nil)
svc.SetConnectionsManager(connMgr)

return &TestService{
Expand Down
16 changes: 10 additions & 6 deletions core/services/job/job_orm_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -796,7 +796,7 @@ func TestORM_CreateJob_OCR2_DuplicatedContractAddress(t *testing.T) {

_, address := cltest.MustInsertRandomKey(t, keyStore.Eth())

jb, err := ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jb, err := ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)

const juelsPerFeeCoinSource = `
Expand All @@ -812,7 +812,7 @@ func TestORM_CreateJob_OCR2_DuplicatedContractAddress(t *testing.T) {
err = jobORM.CreateJob(&jb)
require.NoError(t, err)

jb2, err := ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jb2, err := ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)

jb2.Name = null.StringFrom("Job with same chain id & contract address")
Expand All @@ -822,7 +822,7 @@ func TestORM_CreateJob_OCR2_DuplicatedContractAddress(t *testing.T) {
err = jobORM.CreateJob(&jb2)
require.Error(t, err)

jb3, err := ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jb3, err := ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)
jb3.Name = null.StringFrom("Job with different chain id & same contract address")
jb3.OCR2OracleSpec.TransmitterID = null.StringFrom(address.String())
Expand Down Expand Up @@ -855,7 +855,7 @@ func TestORM_CreateJob_OCR2_Sending_Keys_Transmitter_Keys_Validations(t *testing

jobORM := NewTestORM(t, db, pipelineORM, bridgesORM, keyStore, config.Database())

jb, err := ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jb, err := ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)

t.Run("sending keys or transmitterID must be defined", func(t *testing.T) {
Expand Down Expand Up @@ -896,7 +896,7 @@ func TestORM_ValidateKeyStoreMatch(t *testing.T) {
var jb job.Job
{
var err error
jb, err = ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jb, err = ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)
}

Expand Down Expand Up @@ -1088,7 +1088,7 @@ func Test_FindJob(t *testing.T) {
)
require.NoError(t, err)

jobOCR2, err := ocr2validate.ValidatedOracleSpecToml(config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal())
jobOCR2, err := ocr2validate.ValidatedOracleSpecToml(testutils.Context(t), config.OCR2(), config.Insecure(), testspecs.GetOCR2EVMSpecMinimal(), nil)
require.NoError(t, err)
jobOCR2.OCR2OracleSpec.TransmitterID = null.StringFrom(address.String())

Expand All @@ -1103,16 +1103,20 @@ func Test_FindJob(t *testing.T) {
ocr2WithFeedID1 := "0x0001000000000000000000000000000000000000000000000000000000000001"
ocr2WithFeedID2 := "0x0001000000000000000000000000000000000000000000000000000000000002"
jobOCR2WithFeedID1, err := ocr2validate.ValidatedOracleSpecToml(
testutils.Context(t),
config.OCR2(),
config.Insecure(),
fmt.Sprintf(mercuryOracleTOML, cltest.DefaultCSAKey.PublicKeyString(), ocr2WithFeedID1),
nil,
)
require.NoError(t, err)

jobOCR2WithFeedID2, err := ocr2validate.ValidatedOracleSpecToml(
testutils.Context(t),
config.OCR2(),
config.Insecure(),
fmt.Sprintf(mercuryOracleTOML, cltest.DefaultCSAKey.PublicKeyString(), ocr2WithFeedID2),
nil,
)
jobOCR2WithFeedID2.ExternalJobID = uuid.New()
jobOCR2WithFeedID2.Name = null.StringFrom("new name")
Expand Down
Loading
Loading