Beispiel #1
0
// HookContext is part of the ContextFactory interface.
func (f *contextFactory) HookContext(hookInfo hook.Info) (*HookContext, error) {
	ctx, err := f.coreContext()
	if err != nil {
		return nil, errors.Trace(err)
	}
	hookName := string(hookInfo.Kind)
	if hookInfo.Kind.IsRelation() {
		ctx.relationId = hookInfo.RelationId
		ctx.remoteUnitName = hookInfo.RemoteUnit
		relation, found := ctx.relations[hookInfo.RelationId]
		if !found {
			return nil, errors.Errorf("unknown relation id: %v", hookInfo.RelationId)
		}
		if hookInfo.Kind == hooks.RelationDeparted {
			relation.cache.RemoveMember(hookInfo.RemoteUnit)
		} else if hookInfo.RemoteUnit != "" {
			// Clear remote settings cache for changing remote unit.
			relation.cache.InvalidateMember(hookInfo.RemoteUnit)
		}
		hookName = fmt.Sprintf("%s-%s", relation.Name(), hookInfo.Kind)
	}
	if hookInfo.Kind.IsStorage() {
		ctx.storageTag = names.NewStorageTag(hookInfo.StorageId)
		if _, found := ctx.storage.Storage(ctx.storageTag); !found {
			return nil, errors.Errorf("unknown storage id: %v", hookInfo.StorageId)
		}
		storageName, err := names.StorageName(hookInfo.StorageId)
		if err != nil {
			return nil, errors.Trace(err)
		}
		hookName = fmt.Sprintf("%s-%s", storageName, hookName)
	}
	// Metrics are only sent from the collect-metrics hook.
	if hookInfo.Kind == hooks.CollectMetrics {
		ch, err := getCharm(f.paths.GetCharmDir())
		if err != nil {
			return nil, errors.Trace(err)
		}
		ctx.definedMetrics = ch.Metrics()

		chURL, err := f.unit.CharmURL()
		if err != nil {
			return nil, errors.Trace(err)
		}

		charmMetrics := map[string]charm.Metric{}
		if ch.Metrics() != nil {
			charmMetrics = ch.Metrics().Metrics
		}
		ctx.metricsRecorder, err = metrics.NewJSONMetricRecorder(
			f.paths.GetMetricsSpoolDir(),
			charmMetrics,
			chURL.String())
		if err != nil {
			return nil, errors.Trace(err)
		}
	}
	ctx.id = f.newId(hookName)
	return ctx, nil
}
Beispiel #2
0
func (s *MetricsReaderSuite) SetUpTest(c *gc.C) {
	s.paths = newTestPaths(c)

	var err error
	s.w, err = metrics.NewJSONMetricRecorder(
		s.paths.GetMetricsSpoolDir(),
		map[string]corecharm.Metric{"pings": corecharm.Metric{}},
		"local:precise/wordpress")

	c.Assert(err, jc.ErrorIsNil)
	err = s.w.AddMetric("pings", "5", time.Now())
	c.Assert(err, jc.ErrorIsNil)
	err = s.w.Close()
	c.Assert(err, jc.ErrorIsNil)
}
Beispiel #3
0
func (s *MetricsRecorderSuite) TestUnknownMetricKey(c *gc.C) {
	w, err := metrics.NewJSONMetricRecorder(s.paths.GetMetricsSpoolDir(), map[string]corecharm.Metric{}, "local:precise/wordpress")
	c.Assert(err, jc.ErrorIsNil)
	c.Assert(w, gc.NotNil)
	err = w.AddMetric("pings", "5", time.Now())
	c.Assert(err, gc.ErrorMatches, `metric key "pings" not declared by the charm`)
	err = w.Close()
	c.Assert(err, jc.ErrorIsNil)

	r, err := metrics.NewJSONMetricReader(s.paths.GetMetricsSpoolDir())
	c.Assert(err, jc.ErrorIsNil)
	batches, err := r.Read()
	c.Assert(err, jc.ErrorIsNil)
	c.Assert(batches, gc.HasLen, 0)
}
Beispiel #4
0
func (s *MetricsOperationSuite) SetUpTest(c *gc.C) {
	s.spoolDir = c.MkDir()

	declaredMetrics := map[string]corecharm.Metric{
		"pings": corecharm.Metric{Description: "test pings", Type: corecharm.MetricTypeAbsolute},
	}
	recorder, err := metrics.NewJSONMetricRecorder(s.spoolDir, declaredMetrics, "local:trusty/testcharm")
	c.Assert(err, jc.ErrorIsNil)

	err = recorder.AddMetric("pings", "50", time.Now())
	c.Assert(err, jc.ErrorIsNil)

	err = recorder.Close()
	c.Assert(err, jc.ErrorIsNil)
}
Beispiel #5
0
func (s addMetrics) step(c *gc.C, ctx *context) {
	var declaredMetrics map[string]corecharm.Metric
	if ctx.sch.Metrics() != nil {
		declaredMetrics = ctx.sch.Metrics().Metrics
	}
	spoolDir := filepath.Join(ctx.path, "state", "spool", "metrics")

	recorder, err := metrics.NewJSONMetricRecorder(spoolDir, declaredMetrics, ctx.sch.URL().String())
	c.Assert(err, jc.ErrorIsNil)

	for _, value := range s.values {
		recorder.AddMetric("pings", value, time.Now())
	}

	err = recorder.Close()
	c.Assert(err, jc.ErrorIsNil)
}
Beispiel #6
0
func (s *MetricsRecorderSuite) TestInit(c *gc.C) {
	w, err := metrics.NewJSONMetricRecorder(s.paths.GetMetricsSpoolDir(), map[string]corecharm.Metric{"pings": corecharm.Metric{}}, "local:precise/wordpress")
	c.Assert(err, jc.ErrorIsNil)
	c.Assert(w, gc.NotNil)
	err = w.AddMetric("pings", "5", time.Now())
	c.Assert(err, jc.ErrorIsNil)
	err = w.Close()
	c.Assert(err, jc.ErrorIsNil)

	r, err := metrics.NewJSONMetricReader(s.paths.GetMetricsSpoolDir())
	c.Assert(err, jc.ErrorIsNil)
	batches, err := r.Read()
	c.Assert(err, jc.ErrorIsNil)
	c.Assert(batches, gc.HasLen, 1)
	batch := batches[0]
	c.Assert(batch.CharmURL, gc.Equals, "local:precise/wordpress")
	c.Assert(batch.UUID, gc.Not(gc.Equals), "")
	c.Assert(batch.Metrics, gc.HasLen, 1)
	c.Assert(batch.Metrics[0].Key, gc.Equals, "pings")
	c.Assert(batch.Metrics[0].Value, gc.Equals, "5")

	err = r.Close()
	c.Assert(err, jc.ErrorIsNil)
}
Beispiel #7
0
func NewHookContext(
	unit *uniter.Unit,
	state *uniter.State,
	id,
	uuid,
	envName string,
	relationId int,
	remoteUnitName string,
	relations map[int]*ContextRelation,
	apiAddrs []string,
	serviceOwner names.UserTag,
	proxySettings proxy.Settings,
	canAddMetrics bool,
	charmMetrics *charm.Metrics,
	actionData *ActionData,
	assignedMachineTag names.MachineTag,
	paths Paths,
) (*HookContext, error) {
	ctx := &HookContext{
		unit:               unit,
		state:              state,
		id:                 id,
		uuid:               uuid,
		envName:            envName,
		unitName:           unit.Name(),
		relationId:         relationId,
		remoteUnitName:     remoteUnitName,
		relations:          relations,
		apiAddrs:           apiAddrs,
		serviceOwner:       serviceOwner,
		proxySettings:      proxySettings,
		metricsRecorder:    nil,
		definedMetrics:     charmMetrics,
		actionData:         actionData,
		pendingPorts:       make(map[PortRange]PortRangeInfo),
		assignedMachineTag: assignedMachineTag,
	}
	if canAddMetrics {
		charmURL, err := unit.CharmURL()
		if err != nil {
			return nil, err
		}
		ctx.metricsRecorder, err = metrics.NewJSONMetricRecorder(
			paths.GetMetricsSpoolDir(),
			charmMetrics.Metrics,
			charmURL.String())
		if err != nil {
			return nil, err
		}
	}
	// Get and cache the addresses.
	var err error
	ctx.publicAddress, err = unit.PublicAddress()
	if err != nil && !params.IsCodeNoAddressSet(err) {
		return nil, err
	}
	ctx.privateAddress, err = unit.PrivateAddress()
	if err != nil && !params.IsCodeNoAddressSet(err) {
		return nil, err
	}
	ctx.availabilityzone, err = unit.AvailabilityZone()
	if err != nil {
		return nil, err
	}
	ctx.machinePorts, err = state.AllMachinePorts(ctx.assignedMachineTag)
	if err != nil {
		return nil, errors.Trace(err)
	}

	statusCode, statusInfo, err := unit.MeterStatus()
	if err != nil {
		return nil, errors.Annotate(err, "could not retrieve meter status for unit")
	}
	ctx.meterStatus = &meterStatus{
		code: statusCode,
		info: statusInfo,
	}
	return ctx, nil
}