// GetNotifications is handler for GET /users/{username}/notifications
// Get the list of notifications, these are pending invitations or approvals
188304
func (api UsersAPI) GetNotifications(w http.ResponseWriter, r *http.Request) {
	username := mux.Vars(r)["username"]

	type NotificationList struct {
		Approvals               []invitations.JoinOrganizationInvitation `json:"approvals"`
		ContractRequests        []contractdb.ContractSigningRequest      `json:"contractRequests"`
		Invitations             []invitations.JoinOrganizationInvitation `json:"invitations"`
		MissingScopes           []organizationDb.MissingScope            `json:"missingscopes"`
		OrganizationInvitations []invitations.JoinOrganizationInvitation `json:"organizationinvitations"`
	}
	var notifications NotificationList

	invitationMgr := invitations.NewInvitationManager(r)
	valMgr := validationdb.NewManager(r)

	userOrgRequests, err := invitationMgr.FilterByUser(username, "pending")
	if handleServerError(w, "getting invitations by user", err) {
		return
	}

	// Add the invites for the users verified phone numbers. This is required if the invite
	// was added before the phone number was verified, and no invite sms was send
	validatedPhonenumbers, err := valMgr.GetByUsernameValidatedPhonenumbers(username)
	if handleServerError(w, "getting verified phone numbers", err) {
		return
	}
	for _, number := range validatedPhonenumbers {
		phonenumberRequests, err := invitationMgr.FilterByPhonenumber(number.Phonenumber, "pending")
		if handleServerError(w, "getting invitations by user for phonenumber", err) {
			return
		}
		userOrgRequests = append(userOrgRequests, phonenumberRequests...)
	}

	// Add the invites for the users verified email addresses. This is required if the invite
	// was added before the email address was verified, and no invite email was send
	validatedEmailaddresses, err := valMgr.GetByUsernameValidatedEmailAddress(username)
	if handleServerError(w, "getting verified email addresses", err) {
		return
	}
	for _, email := range validatedEmailaddresses {
		emailRequests, err := invitationMgr.FilterByEmail(email.EmailAddress, "pending")
		if handleServerError(w, "getting invitations by user for email", err) {
			return
		}
		for _, emailRequest := range emailRequests {
			alreadyFound := false
			for _, inv := range userOrgRequests {
				if inv.Organization == emailRequest.Organization {
					alreadyFound = true
					break
				}
			}
			if !alreadyFound {
				userOrgRequests = append(userOrgRequests, emailRequest)
			}
		}
	}

	// Add the invites for the organizations where this user is an owner
	orgMgr := organizationDb.NewManager(r)

	orgs, err := orgMgr.AllByUser(username)
	if err != nil {
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	var ownedOrgs []string

	for _, org := range orgs {
		if exists(username, org.Owners) {
			ownedOrgs = append(ownedOrgs, org.Globalid)
		}
	}

	orgInvites := make([]invitations.JoinOrganizationInvitation, 0)

	for _, org := range ownedOrgs {
		invites, err := invitationMgr.GetOpenOrganizationInvites(org)
		if err != nil {
			log.Error("Error while loading all invites where the organization ", org, " is invited")
			http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
			return
		}
		orgInvites = append(orgInvites, invites...)
	}

	notifications.Invitations = userOrgRequests
	notifications.OrganizationInvitations = orgInvites
	// TODO: Get Approvals and Contract requests
	notifications.Approvals = []invitations.JoinOrganizationInvitation{}
	notifications.ContractRequests = []contractdb.ContractSigningRequest{}
	extraOrganizations := []string{}
	for _, invitation := range notifications.Invitations {
		extraOrganizations = append(extraOrganizations, invitation.Organization)
	}
	err, notifications.MissingScopes = getMissingScopesForOrganizations(r, username, extraOrganizations)
	if handleServerError(w, "getting missing scopes", err) {
		return
	}
	w.Header().Set("Content-type", "application/json")
	json.NewEncoder(w).Encode(&notifications)
}
157748
func (m *Machine) RegisterNotifier(services ...NotificationService) {
	for _, service := range services {
		m.notifiers = append(m.notifiers, service)
	}
}
145197
func (s *userServiceImpl) NotifyIdentitiesBeforeDeactivation(ctx context.Context, now func() time.Time) ([]repository.Identity, error) {
	since := now().Add(-s.config.GetUserDeactivationInactivityNotificationPeriodDays()) // remove 'n' days from now (default: 24)
	limit := s.config.GetUserDeactivationFetchLimit()
	identities, err := s.Repositories().Identities().ListIdentitiesToNotifyForDeactivation(ctx, since, limit)
	if err != nil {
		return nil, errs.Wrap(err, "unable to send notification to users before account deactivation")
	}
	// for each identity, send a notification and record the timestamp in a separate transaction.
	// perform the task for each identity in a separate Tx, and just log the error if something wrong happened,
	// but don't stop processing on the rest of the accounts.
	expirationDate := GetExpiryDate(s.config, now)
	// run the notification/record update in a separate routine, with pooling of child routines to avoid
	// sending too many requests at once to the notification service and to the database
	defer ants.Release()
	var wg sync.WaitGroup
	p, err := ants.NewPoolWithFunc(10, func(id interface{}) {
		defer wg.Done()
		identity, ok := id.(repository.Identity)
		// just to make sure that the arg type is valid.
		if !ok {
			log.Error(ctx, map[string]interface{}{}, "argument is not an identity")
			return
		}
		err := s.notifyIdentityBeforeDeactivation(ctx, identity, expirationDate, now)
		if err != nil {
			log.Error(ctx, map[string]interface{}{
				"error":    err,
				"username": identity.Username,
			}, "error while notifying user before account deactivation")
		} else {
			log.Info(ctx, map[string]interface{}{
				"username": identity.Username,
			}, "notified user before account deactivation")
		}
		// include a small delay to give time to notification service and database to handle the requests
		time.Sleep(s.config.GetPostDeactivationNotificationDelayMillis())
	})
	if err != nil {
		return nil, errs.Wrap(err, "unable to send notification to users before account deactivation")
	}

	defer func() {
		err := p.Release()
		if err != nil {
			log.Error(ctx, map[string]interface{}{
				"error": err,
			}, "error while releasing the go routine pool")
		}
	}()
	for _, identity := range identities {
		wg.Add(1)
		err := p.Invoke(identity)
		if err != nil {
			log.Error(ctx, map[string]interface{}{
				"error": err,
			}, "error while notifying about account deactivation")
		}
	}
	wg.Wait()
	return identities, nil
}
744395
func (s *NotificationServer) TransactionNotifications() TransactionNotificationsClient {
	c := make(chan *TransactionNotifications)
	s.mu.Lock()
	s.transactions = append(s.transactions, c)
	s.mu.Unlock()
	return TransactionNotificationsClient{
		C:      c,
		server: s,
	}
}
348446
func (r Network_Storage) GetNotificationSubscribers() (resp []datatypes.Notification_User_Subscriber, err error) {
	err = r.Session.DoRequest("SoftLayer_Network_Storage", "getNotificationSubscribers", nil, &r.Options, &resp)
	return
}
212409
func (c *ConfigurationData) GetUserDeactivationInactivityNotificationPeriodDays() time.Duration {
	return time.Duration(c.v.GetInt(varUserDeactivationInactivityNotificationPeriodDays)) * 24 * time.Hour
}
1001226
func (c *ConsulAlertClient) CustomNotifiers() (customNotifs map[string]string) {
	if kvPairs, _, err := c.api.KV().List("consul-alerts/config/notifiers/custom", nil); err == nil {
		customNotifs = make(map[string]string)
		for _, kvPair := range kvPairs {
			rp := regexp.MustCompile("/([^/]*)$")
			match := rp.FindStringSubmatch(kvPair.Key)
			custNotifName := match[1]
			if custNotifName == "" {
				continue
			}
			customNotifs[custNotifName] = string(kvPair.Value)
		}
	}
	return customNotifs
}
422298
func (a *API) GetNotification(user int, id int) (*Notification, error) {
	dst := new(Notification)
	url := a.BuildURL("/v2/user/%d/notification/%d", user, id)
	err := a.Get(url, Params{}, dst)
	return dst, err
}
448786
func (c *ConsulAlertClient) GetReminders() []notifier.Message {
	remindersList, _, _ := c.api.KV().List("consul-alerts/reminders", nil)
	var messages []notifier.Message
	for _, kvpair := range remindersList {
		var message notifier.Message
		json.Unmarshal(kvpair.Value, &message)
		messages = append(messages, message)
	}
	log.Println("Getting reminders")
	return messages
}
453845
func (b *Listeners) Notify() {
	b.Lock()
	defer b.Unlock()
	for _, notify := range b.listeners {
		notify()
	}
}
464285
func SupportedNotifiers() []string {
	registerMtx.Lock()
	defer registerMtx.Unlock()

	supportedNotifiers := make([]string, 0, len(notifiers))
	for driverName := range notifiers {
		supportedNotifiers = append(supportedNotifiers, driverName)
	}

	return supportedNotifiers
}
216698
func (c *Connection) isNotificationMessage(msgID uint16) bool {
	c.subscriptionsLock.RLock()
	defer c.subscriptionsLock.RUnlock()

	_, exists := c.subscriptions[msgID]
	return exists
}
1111129
func (r Notification_User_Subscriber_Preference) GetNotificationUserSubscriber() (resp datatypes.Notification_User_Subscriber, err error) {
	err = r.Session.DoRequest("SoftLayer_Notification_User_Subscriber_Preference", "getNotificationUserSubscriber", nil, &r.Options, &resp)
	return
}
425795
func (s *AssessmentRun) SetNotifications(v []*AssessmentRunNotification) *AssessmentRun {
	s.Notifications = v
	return s
}
533741
func (handle *ContextHandle) sendNotification() {
	if handle.reloadNotification != nil {
		select {
		case handle.reloadNotification <- struct{}{}:
			logger.Info("Notification sent for recreated pkcs11 ctx")
		default:
			logger.Warn("Unable to send notification for recreated pkcs11 ctx")
		}
	}
}
1024060
func (s *DescribeNotificationsForBudgetOutput) SetNotifications(v []*Notification) *DescribeNotificationsForBudgetOutput {
	s.Notifications = v
	return s
}
650372
func (m *wsNotificationManager) notificationHandler() {
	// clients is a map of all currently connected websocket clients.
	clients := make(map[chan struct{}]*wsClient)

	// Maps used to hold lists of websocket clients to be notified on
	// certain events.  Each websocket client also keeps maps for the events
	// which have multiple triggers to make removal from these lists on
	// connection close less horrendously expensive.
	//
	// Where possible, the quit channel is used as the unique id for a client
	// since it is quite a bit more efficient than using the entire struct.
	blockNotifications := make(map[chan struct{}]*wsClient)
	txNotifications := make(map[chan struct{}]*wsClient)
	watchedOutPoints := make(map[wire.OutPoint]map[chan struct{}]*wsClient)
	watchedAddrs := make(map[string]map[chan struct{}]*wsClient)

out:
	for {
		select {
		case n, ok := <-m.notificationMsgs:
			if !ok {
				// queueHandler quit.
				break out
			}
			switch n := n.(type) {
			case *notificationBlockConnected:
				block := (*btcutil.Block)(n)

				// Skip iterating through all txs if no
				// tx notification requests exist.
				if len(watchedOutPoints) != 0 || len(watchedAddrs) != 0 {
					for _, tx := range block.Transactions() {
						m.notifyForTx(watchedOutPoints,
							watchedAddrs, tx, block)
					}
				}

				if len(blockNotifications) != 0 {
					m.notifyBlockConnected(blockNotifications,
						block)
					m.notifyFilteredBlockConnected(blockNotifications,
						block)
				}

			case *notificationBlockDisconnected:
				block := (*btcutil.Block)(n)

				if len(blockNotifications) != 0 {
					m.notifyBlockDisconnected(blockNotifications,
						block)
					m.notifyFilteredBlockDisconnected(blockNotifications,
						block)
				}

			case *notificationTxAcceptedByMempool:
				if n.isNew && len(txNotifications) != 0 {
					m.notifyForNewTx(txNotifications, n.tx)
				}
				m.notifyForTx(watchedOutPoints, watchedAddrs, n.tx, nil)
				m.notifyRelevantTxAccepted(n.tx, clients)

			case *notificationRegisterBlocks:
				wsc := (*wsClient)(n)
				blockNotifications[wsc.quit] = wsc

			case *notificationUnregisterBlocks:
				wsc := (*wsClient)(n)
				delete(blockNotifications, wsc.quit)

			case *notificationRegisterClient:
				wsc := (*wsClient)(n)
				clients[wsc.quit] = wsc

			case *notificationUnregisterClient:
				wsc := (*wsClient)(n)
				// Remove any requests made by the client as well as
				// the client itself.
				delete(blockNotifications, wsc.quit)
				delete(txNotifications, wsc.quit)
				for k := range wsc.spentRequests {
					op := k
					m.removeSpentRequest(watchedOutPoints, wsc, &op)
				}
				for addr := range wsc.addrRequests {
					m.removeAddrRequest(watchedAddrs, wsc, addr)
				}
				delete(clients, wsc.quit)

			case *notificationRegisterSpent:
				m.addSpentRequests(watchedOutPoints, n.wsc, n.ops)

			case *notificationUnregisterSpent:
				m.removeSpentRequest(watchedOutPoints, n.wsc, n.op)

			case *notificationRegisterAddr:
				m.addAddrRequests(watchedAddrs, n.wsc, n.addrs)

			case *notificationUnregisterAddr:
				m.removeAddrRequest(watchedAddrs, n.wsc, n.addr)

			case *notificationRegisterNewMempoolTxs:
				wsc := (*wsClient)(n)
				txNotifications[wsc.quit] = wsc

			case *notificationUnregisterNewMempoolTxs:
				wsc := (*wsClient)(n)
				delete(txNotifications, wsc.quit)

			default:
				rpcsLog.Warn("Unhandled notification type")
			}

		case m.numClients <- len(clients):

		case <-m.quit:
			// RPC server shutting down.
			break out
		}
	}

	for _, c := range clients {
		c.Disconnect()
	}
	m.wg.Done()
}