コード例 #1
0
ファイル: server.go プロジェクト: TheThingsNetwork/ttn
func (s *networkServerRPC) PrepareActivation(ctx context.Context, activation *broker.DeduplicatedDeviceActivationRequest) (*broker.DeduplicatedDeviceActivationRequest, error) {
	if err := s.ValidateContext(ctx); err != nil {
		return nil, err
	}
	if err := activation.Validate(); err != nil {
		return nil, errors.Wrap(err, "Invalid Activation Request")
	}
	res, err := s.networkServer.HandlePrepareActivation(activation)
	if err != nil {
		return nil, err
	}
	return res, nil
}
コード例 #2
0
ファイル: server.go プロジェクト: TheThingsNetwork/ttn
func (h *handlerRPC) Activate(ctx context.Context, activation *pb_broker.DeduplicatedDeviceActivationRequest) (*pb.DeviceActivationResponse, error) {
	_, err := h.handler.ValidateNetworkContext(ctx)
	if err != nil {
		return nil, err
	}
	if err := activation.Validate(); err != nil {
		return nil, errors.Wrap(err, "Invalid Activation Request")
	}
	res, err := h.handler.HandleActivation(activation)
	if err != nil {
		return nil, err
	}
	return res, nil
}
コード例 #3
0
ファイル: activation.go プロジェクト: TheThingsNetwork/ttn
func (n *networkServer) HandlePrepareActivation(activation *pb_broker.DeduplicatedDeviceActivationRequest) (*pb_broker.DeduplicatedDeviceActivationRequest, error) {
	if activation.AppEui == nil || activation.DevEui == nil {
		return nil, errors.NewErrInvalidArgument("Activation", "missing AppEUI or DevEUI")
	}
	dev, err := n.devices.Get(*activation.AppEui, *activation.DevEui)
	if err != nil {
		return nil, err
	}
	activation.AppId = dev.AppID
	activation.DevId = dev.DevID

	// Get activation constraints (for DevAddr prefix selection)
	activationConstraints := strings.Split(dev.Options.ActivationConstraints, ",")
	if len(activationConstraints) == 1 && activationConstraints[0] == "" {
		activationConstraints = []string{}
	}
	activationConstraints = append(activationConstraints, "otaa")

	// Build activation metadata if not present
	if meta := activation.GetActivationMetadata(); meta == nil {
		activation.ActivationMetadata = &pb_protocol.ActivationMetadata{}
	}
	// Build lorawan metadata if not present
	if lorawan := activation.ActivationMetadata.GetLorawan(); lorawan == nil {
		return nil, errors.NewErrInvalidArgument("Activation", "missing LoRaWAN metadata")
	}

	// Build response template if not present
	if pld := activation.GetResponseTemplate(); pld == nil {
		return nil, errors.NewErrInvalidArgument("Activation", "missing response template")
	}
	lorawanMeta := activation.ActivationMetadata.GetLorawan()

	// Get a random device address
	devAddr, err := n.getDevAddr(activationConstraints...)
	if err != nil {
		return nil, err
	}

	// Set the DevAddr in the Activation Metadata
	lorawanMeta.DevAddr = &devAddr

	// Build JoinAccept Payload
	phy := lorawan.PHYPayload{
		MHDR: lorawan.MHDR{
			MType: lorawan.JoinAccept,
			Major: lorawan.LoRaWANR1,
		},
		MACPayload: &lorawan.JoinAcceptPayload{
			NetID:      n.netID,
			DLSettings: lorawan.DLSettings{RX2DataRate: uint8(lorawanMeta.Rx2Dr), RX1DROffset: uint8(lorawanMeta.Rx1DrOffset)},
			RXDelay:    uint8(lorawanMeta.RxDelay),
			DevAddr:    lorawan.DevAddr(devAddr),
		},
	}
	if lorawanMeta.CfList != nil {
		var cfList lorawan.CFList
		for i, cfListItem := range lorawanMeta.CfList.Freq {
			cfList[i] = cfListItem
		}
		phy.MACPayload.(*lorawan.JoinAcceptPayload).CFList = &cfList
	}

	// Set the Payload
	phyBytes, err := phy.MarshalBinary()
	if err != nil {
		return nil, err
	}
	activation.ResponseTemplate.Payload = phyBytes

	return activation, nil
}