コード例 #1
0
// Get the list organizations a user is owner or member of
// It is handler for GET /users/{username}/organizations
func (api UsersusernameorganizationsAPI) Get(w http.ResponseWriter, r *http.Request) {
	username := mux.Vars(r)["username"]

	orgMgr := organizationdb.NewManager(r)

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

	type UserOrganizations struct {
		Member []string `json:"member"`
		Owner  []string `json:"owner"`
	}
	userOrgs := UserOrganizations{
		Member: []string{},
		Owner:  []string{},
	}

	for _, org := range orgs {
		if exists(username, org.Owners) {
			userOrgs.Owner = append(userOrgs.Owner, org.Globalid)
		} else {
			userOrgs.Member = append(userOrgs.Member, org.Globalid)
		}
	}
	w.Header().Set("Content-type", "application/json")
	json.NewEncoder(w).Encode(&userOrgs)
}
コード例 #2
0
// Set2faValidityTime is the handler for PUT /organizations/globalid/2fa/validity
// Sets the 2fa validity time for the organization, in days
func (api OrganizationsAPI) Set2faValidityTime(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	body := struct {
		SecondsValidity int `json:"secondsvalidity"`
	}{}

	if err := json.NewDecoder(r.Body).Decode(&body); err != nil {
		log.Error("Error while setting 2FA validity time: ", err.Error())
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	mgr := organization.NewManager(r)
	seconds := body.SecondsValidity

	if seconds < 0 {
		seconds = 0
	} else if seconds > 2678400 {
		seconds = 2678400
	}

	err := mgr.SetValidity(globalid, seconds)
	if err != nil {
		log.Error("Error while setting 2FA validity time: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.WriteHeader(http.StatusOK)
}
コード例 #3
0
func (api OrganizationsAPI) DeleteDns(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	dnsName := mux.Vars(r)["dnsname"]

	orgMgr := organization.NewManager(r)
	organization, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}
	sort.Strings(organization.DNS)
	if sort.SearchStrings(organization.DNS, dnsName) == len(organization.DNS) {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	err = orgMgr.RemoveDNS(organization, dnsName)

	if err != nil {
		log.Error("Error removing DNS name", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")

	w.WriteHeader(http.StatusNoContent)
}
コード例 #4
0
// Get2faValidityTime is the handler for GET /organizations/globalid/2fa/validity
// Get the 2fa validity time for the organization, in seconds
func (api OrganizationsAPI) Get2faValidityTime(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	mgr := organization.NewManager(r)

	validity, err := mgr.GetValidity(globalid)
	if err != nil && err != mgo.ErrNotFound {
		log.Error("Error while getting validity duration: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if err == mgo.ErrNotFound {
		log.Error("Error while getting validity duration: organization nout found")
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	response := struct {
		SecondsValidity int `json:"secondsvalidity"`
	}{
		SecondsValidity: validity,
	}

	w.Header().Set("Content-Type", "application/json")
	json.NewEncoder(w).Encode(response)
}
コード例 #5
0
// Accept membership in organization
// It is handler for POST /users/{username}/organizations/{globalid}/roles/{role}
func (api UsersusernameorganizationsAPI) globalidrolesrolePost(w http.ResponseWriter, r *http.Request) {
	username := mux.Vars(r)["username"]
	role := mux.Vars(r)["role"]
	organization := mux.Vars(r)["globalid"]

	var j invitations.JoinOrganizationInvitation

	if err := json.NewDecoder(r.Body).Decode(&j); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgReqMgr := invitations.NewInvitationManager(r)

	orgRequest, err := orgReqMgr.Get(username, organization, role, invitations.RequestPending)
	if err != nil {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	// TODO: Save member
	orgMgr := organizationdb.NewManager(r)

	if org, err := orgMgr.GetByName(organization); err != nil {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	} else {
		if invitations.RoleOwner == orgRequest.Role {
			// Accepted Owner role
			if err := orgMgr.SaveOwner(org, username); err != nil {
				log.Error("Failed to save owner: ", username)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
		} else {
			// Accepted member role
			if err := orgMgr.SaveMember(org, username); err != nil {
				log.Error("Failed to save member: ", username)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
		}
	}

	orgRequest.Status = invitations.RequestAccepted

	if err := orgReqMgr.Save(orgRequest); err != nil {
		log.Error("Failed to update org request status: ", orgRequest.Organization)
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-type", "application/json")
	w.WriteHeader(http.StatusCreated)

	json.NewEncoder(w).Encode(orgRequest)
}
コード例 #6
0
// AddOrganizationOwner It is handler for POST /organizations/{globalid}/owners
func (api OrganizationsAPI) AddOrganizationOwner(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	var s searchMember

	if err := json.NewDecoder(r.Body).Decode(&s); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgMgr := organization.NewManager(r)

	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}

	u, err := SearchUser(r, s.SearchString)
	if err != nil {
		log.Error(err)
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}
	for _, membername := range org.Owners {
		if membername == u.Username {
			http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
			return
		}
	}
	// Create JoinRequest
	invitationMgr := invitations.NewInvitationManager(r)

	orgReq := &invitations.JoinOrganizationInvitation{
		Role:         invitations.RoleOwner,
		Organization: globalid,
		User:         u.Username,
		Status:       invitations.RequestPending,
		Created:      db.DateTime(time.Now()),
	}

	if err := invitationMgr.Save(orgReq); err != nil {
		log.Error("Error inviting owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	w.WriteHeader(http.StatusCreated)

	json.NewEncoder(w).Encode(orgReq)
}
コード例 #7
0
func (api OrganizationsAPI) actualOrganizationCreation(org organization.Organization, w http.ResponseWriter, r *http.Request) {

	if strings.TrimSpace(org.Globalid) == itsyouonlineGlobalID {
		log.Debug("Duplicate organization")
		http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
		return
	}

	if !org.IsValid() {
		log.Debug("Invalid organization")
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	username := context.Get(r, "authenticateduser").(string)
	orgMgr := organization.NewManager(r)
	logoMgr := organization.NewLogoManager(r)
	count, err := orgMgr.CountByUser(username)
	if err != nil {
		log.Error(err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if count >= MAX_ORGANIZATIONS_PER_USER {
		log.Error("Reached organization limit for user ", username)
		writeErrorResponse(w, 422, "maximum_amount_of_organizations_reached")
		return
	}
	err = orgMgr.Create(&org)

	if err != nil && err != db.ErrDuplicate {
		log.Error(err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	if err == db.ErrDuplicate {
		log.Debug("Duplicate organization")
		http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
		return
	}
	err = logoMgr.Create(&org)

	if err != nil && err != db.ErrDuplicate {
		log.Error(err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	w.WriteHeader(http.StatusCreated)

	json.NewEncoder(w).Encode(&org)
}
コード例 #8
0
// GetOrganizationTree is the handler for GET /organizations/{globalid}/tree
// Get organization tree.
func (api OrganizationsAPI) GetOrganizationTree(w http.ResponseWriter, r *http.Request) {
	var requestedOrganization = mux.Vars(r)["globalid"]
	//TODO: validate input
	parentGlobalID := ""
	var parentGlobalIDs = make([]string, 0, 1)
	for _, localParentID := range strings.Split(requestedOrganization, ".") {
		if parentGlobalID == "" {
			parentGlobalID = localParentID
		} else {
			parentGlobalID = parentGlobalID + "." + localParentID
		}

		parentGlobalIDs = append(parentGlobalIDs, parentGlobalID)
	}

	orgMgr := organization.NewManager(r)

	parentOrganizations, err := orgMgr.GetOrganizations(parentGlobalIDs)

	if err != nil {
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	suborganizations, err := orgMgr.GetSubOrganizations(requestedOrganization)
	if err != nil {
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	allOrganizations := append(parentOrganizations, suborganizations...)

	sort.Sort(byGlobalID(allOrganizations))

	//Build a treestructure
	var orgTree *OrganizationTreeItem
	orgTreeIndex := make(map[string]*OrganizationTreeItem)
	for _, org := range allOrganizations {
		newTreeItem := &OrganizationTreeItem{GlobalID: org.Globalid, Children: make([]*OrganizationTreeItem, 0, 0)}
		orgTreeIndex[org.Globalid] = newTreeItem
		if orgTree == nil {
			orgTree = newTreeItem
		} else {
			path := strings.Split(org.Globalid, ".")
			localName := path[len(path)-1]
			parentTreeItem := orgTreeIndex[strings.TrimSuffix(org.Globalid, "."+localName)]
			parentTreeItem.Children = append(parentTreeItem.Children, newTreeItem)
		}
	}

	w.Header().Set("Content-Type", "application/json")
	json.NewEncoder(w).Encode(orgTree)
}
コード例 #9
0
// GetOrganization Get organization info
// It is handler for GET /organizations/{globalid}
func (api OrganizationsAPI) GetOrganization(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	orgMgr := organization.NewManager(r)

	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}
	json.NewEncoder(w).Encode(org)
}
コード例 #10
0
func (api OrganizationsAPI) UpdateDns(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	oldDns := mux.Vars(r)["dnsname"]

	body := struct {
		Name string
	}{}

	if err := json.NewDecoder(r.Body).Decode(&body); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}
	if !isValidDNSName(body.Name) {
		log.Debug("Invalid DNS name: ", body.Name)
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgMgr := organization.NewManager(r)
	organization, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}
	err = orgMgr.UpdateDNS(organization, oldDns, body.Name)

	if err != nil {
		log.Error("Error updating DNS name", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	response := struct {
		Name string `json:"name"`
	}{
		Name: body.Name,
	}

	w.Header().Set("Content-Type", "application/json")

	w.WriteHeader(http.StatusCreated)
	json.NewEncoder(w).Encode(response)
}
コード例 #11
0
// DeleteOrgOwner is the handler for Delete /organizations/globalid/orgowner/globalid2
// Removes an organization as an owner of this one.
func (api OrganizationsAPI) DeleteOrgOwner(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	orgOwner := mux.Vars(r)["globalid2"]

	mgr := organization.NewManager(r)

	if !mgr.Exists(globalid) {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	// check if OrgOwner is an owner of the organization
	isOwner, err := mgr.OrganizationIsOwner(globalid, orgOwner)
	if err != nil {
		log.Error("Error while removing another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	if !isOwner {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	// now that we know OrgOwner is an OrgOwner of {globalid}, check if the authenticated user is an owner of the OrgOwner
	// the user is known to be an owner of {globalid} since we've required the organization:owner scope
	authenticateduser := context.Get(r, "authenticateduser").(string)
	isOwner, err = mgr.IsOwner(orgOwner, authenticateduser)
	if err != nil {
		log.Error("Error while removing another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if !isOwner {
		http.Error(w, http.StatusText(http.StatusForbidden), http.StatusForbidden)
		return
	}

	err = mgr.RemoveOrganization(globalid, orgOwner)
	if err != nil {
		log.Error("Error while removing another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.WriteHeader(http.StatusNoContent)
}
コード例 #12
0
// It is handler for DELETE /users/{username}/organizations/{globalid}/roles/{role}
func (api UsersusernameorganizationsAPI) globalidrolesroleDelete(w http.ResponseWriter, r *http.Request) {
	username := mux.Vars(r)["username"]
	role := mux.Vars(r)["role"]
	organization := mux.Vars(r)["globalid"]

	orgReqMgr := invitations.NewInvitationManager(r)

	orgRequest, err := orgReqMgr.Get(username, organization, role, invitations.RequestPending)
	if err != nil {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	orgMgr := organizationdb.NewManager(r)

	if org, err := orgMgr.GetByName(organization); err != nil {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	} else {
		if invitations.RoleOwner == orgRequest.Role {
			// Rejected Owner role
			if err := orgMgr.RemoveOwner(org, username); err != nil {
				log.Error("Failed to remove owner: ", username)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
		} else {
			// Rejected member role
			if err := orgMgr.RemoveMember(org, username); err != nil {
				log.Error("Failed to reject member: ", username)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
		}
	}

	orgRequest.Status = invitations.RequestRejected

	if err := orgReqMgr.Save(orgRequest); err != nil {
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.WriteHeader(http.StatusNoContent)
}
コード例 #13
0
func (api OrganizationsAPI) UpdateOrganizationMemberShip(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	var membership Membership
	if err := json.NewDecoder(r.Body).Decode(&membership); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}
	orgMgr := organization.NewManager(r)
	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "updating organization membership", err)
		}
		return
	}
	var oldRole string
	for _, v := range org.Members {
		if v == membership.Username {
			oldRole = "members"
		}
	}
	for _, v := range org.Owners {
		if v == membership.Username {
			oldRole = "owners"
		}
	}
	err = orgMgr.UpdateMembership(globalid, membership.Username, oldRole, membership.Role)
	if err != nil {
		handleServerError(w, "updating organization membership", err)
		return
	}
	org, err = orgMgr.GetByName(globalid)
	if err != nil {
		handleServerError(w, "getting organization", err)
	}
	json.NewEncoder(w).Encode(org)

}
コード例 #14
0
//FilterPossibleScopes filters the requestedScopes to the relevant ones that are possible
// For example, a `user:memberof:orgid1` is not possible if the user is not a member the `orgid1` organization and there is no outstanding invite for this organization
// If allowInvitations is true, invitations to organizations allows the "user:memberof:organization" as possible scopes
func (service *Service) FilterPossibleScopes(r *http.Request, username string, requestedScopes []string, allowInvitations bool) (possibleScopes []string, err error) {
	possibleScopes = make([]string, 0, len(requestedScopes))
	orgmgr := organizationdb.NewManager(r)
	invitationMgr := invitations.NewInvitationManager(r)
	for _, rawscope := range requestedScopes {
		scope := strings.TrimSpace(rawscope)
		if strings.HasPrefix(scope, "user:memberof:") {
			orgid := strings.TrimPrefix(scope, "user:memberof:")
			isMember, err := orgmgr.IsMember(orgid, username)
			if err != nil {
				return nil, err
			}
			if isMember {
				possibleScopes = append(possibleScopes, scope)
				continue
			}
			isOwner, err := orgmgr.IsOwner(orgid, username)
			if err != nil {
				return nil, err
			}
			if isOwner {
				possibleScopes = append(possibleScopes, scope)
				continue
			}
			if allowInvitations {
				hasInvite, err := invitationMgr.HasInvite(orgid, username)
				if err != nil {
					log.Error("FilterPossibleScopes: Error while checking if user has invite for organization: ", err)
					return nil, err
				}
				if hasInvite {
					possibleScopes = append(possibleScopes, scope)
				}
			}
		} else {
			possibleScopes = append(possibleScopes, scope)
		}
	}
	return
}
コード例 #15
0
// UpdateOrganization Updates organization info
// It is handler for PUT /organizations/{globalid}
func (api OrganizationsAPI) UpdateOrganization(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	var org organization.Organization

	if err := json.NewDecoder(r.Body).Decode(&org); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgMgr := organization.NewManager(r)

	oldOrg, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}

	if org.Globalid != globalid {
		http.Error(w, "Changing globalid or id is Forbidden!", http.StatusForbidden)
		return
	}

	// Update only certain fields
	oldOrg.PublicKeys = org.PublicKeys
	oldOrg.DNS = org.DNS

	if err := orgMgr.Save(oldOrg); err != nil {
		log.Error("Error while saving organization: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	json.NewEncoder(w).Encode(oldOrg)
}
コード例 #16
0
// RemoveOrganizationMember Remove a member from organization
// It is handler for DELETE /organizations/{globalid}/members/{username}
func (api OrganizationsAPI) RemoveOrganizationMember(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	username := mux.Vars(r)["username"]

	orgMgr := organization.NewManager(r)

	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}
	if err := orgMgr.RemoveMember(org, username); err != nil {
		log.Error("Error adding member: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.WriteHeader(http.StatusNoContent)
}
コード例 #17
0
// DeleteOrganization is the handler for DELETE /organizations/{globalid}
// Deletes an organization and all data linked to it (join-organization-invitations, oauth_access_tokens, oauth_clients, authorizations)
func (api OrganizationsAPI) DeleteOrganization(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]
	orgMgr := organization.NewManager(r)
	logoMgr := organization.NewLogoManager(r)
	if !orgMgr.Exists(globalid) {
		writeErrorResponse(w, http.StatusNotFound, "organization_not_found")
		return
	}
	suborganizations, err := orgMgr.GetSubOrganizations(globalid)
	if handleServerError(w, "fetching suborganizations", err) {
		return
	}
	if len(suborganizations) != 0 {
		writeErrorResponse(w, 422, "organization_has_children")
		return
	}
	err = orgMgr.Remove(globalid)
	if handleServerError(w, "removing organization", err) {
		return
	}
	// Remove the organizations as a member/ an owner of other organizations
	organizations, err := orgMgr.AllByOrg(globalid)
	if handleServerError(w, "fetching organizations where this org is an owner/a member", err) {
		return
	}
	for _, org := range organizations {
		err = orgMgr.RemoveOrganization(org.Globalid, globalid)
		if handleServerError(w, "removing organizations as a member / an owner of another organization", err) {
			return
		}
	}
	if logoMgr.Exists(globalid) {
		err = logoMgr.Remove(globalid)
		if handleServerError(w, "removing organization logo", err) {
			return
		}
	}
	orgReqMgr := invitations.NewInvitationManager(r)
	err = orgReqMgr.RemoveAll(globalid)
	if handleServerError(w, "removing organization invitations", err) {
		return
	}

	oauthMgr := oauthservice.NewManager(r)
	err = oauthMgr.RemoveTokensByGlobalId(globalid)
	if handleServerError(w, "removing organization oauth accesstokens", err) {
		return
	}
	err = oauthMgr.DeleteAllForOrganization(globalid)
	if handleServerError(w, "removing client secrets", err) {
		return
	}
	err = oauthMgr.RemoveClientsById(globalid)
	if handleServerError(w, "removing organization oauth clients", err) {
		return
	}
	userMgr := user.NewManager(r)
	err = userMgr.DeleteAllAuthorizations(globalid)
	if handleServerError(w, "removing all authorizations", err) {
		return
	}
	err = oauthMgr.RemoveClientsById(globalid)
	if handleServerError(w, "removing organization oauth clients", err) {
		return
	}
	l2faMgr := organization.NewLast2FAManager(r)
	err = l2faMgr.RemoveByOrganization(globalid)
	if handleServerError(w, "removing organization 2FA history", err) {
		return
	}
	w.WriteHeader(http.StatusNoContent)
}
コード例 #18
0
// SetOrgOwner is the handler for POST /organizations/globalid/orgowner
// Sets an organization as an owner of this one.
func (api OrganizationsAPI) SetOrgOwner(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	body := struct {
		OrgOwner string
	}{}

	if err := json.NewDecoder(r.Body).Decode(&body); err != nil {
		log.Debug("Error while adding another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	mgr := organization.NewManager(r)

	// load organization for globalid
	organization, err := mgr.GetByName(globalid)

	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}

	// check if OrgOwner exists
	if !mgr.Exists(body.OrgOwner) {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	// now that we know both organizations exists, check if the authenticated user is an owner of the OrgOwner
	// the user is known to be an owner of the first organization since we've required the organization:owner scope
	authenticateduser := context.Get(r, "authenticateduser").(string)
	isOwner, err := mgr.IsOwner(body.OrgOwner, authenticateduser)
	if err != nil {
		log.Error("Error while adding another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if !isOwner {
		http.Error(w, http.StatusText(http.StatusForbidden), http.StatusForbidden)
		return
	}

	// check if the organization we want to add already exists as a member or an owner
	exists, err := mgr.OrganizationIsPartOf(globalid, body.OrgOwner)
	if err != nil {
		log.Error("Error while checking if this organization is part of another: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if exists {
		http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
		return
	}

	err = mgr.SaveOrgOwner(organization, body.OrgOwner)
	if err != nil {
		log.Error("Error while adding another organization as owner: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.WriteHeader(http.StatusCreated)
}
コード例 #19
0
ファイル: login.go プロジェクト: itsyouonline/identityserver
//ProcessLoginForm logs a user in if the credentials are valid
func (service *Service) ProcessLoginForm(w http.ResponseWriter, request *http.Request) {
	//TODO: validate csrf token
	//TODO: limit the number of failed/concurrent requests

	err := request.ParseForm()
	if err != nil {
		log.Debug("ERROR parsing registration form")
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}
	values := struct {
		Login    string `json:"login"`
		Password string `json:"password"`
	}{}

	if err = json.NewDecoder(request.Body).Decode(&values); err != nil {
		log.Debug("Error decoding the login request:", err)
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	login := strings.ToLower(values.Login)

	u, err := organization.SearchUser(request, login)
	if err == mgo.ErrNotFound {
		w.WriteHeader(422)
		return
	} else if err != nil {
		log.Error("Failed to search for user: "******"client_id")
	// Remove last 2FA entry if an invalid password is entered
	validcredentials := userexists && validpassword
	if !validcredentials {
		if client != "" {
			l2faMgr := organizationdb.NewLast2FAManager(request)
			if l2faMgr.Exists(client, u.Username) {
				l2faMgr.RemoveLast2FA(client, u.Username)
			}
		}
		w.WriteHeader(422)
		return
	}
	loginSession, err := service.GetSession(request, SessionLogin, "loginsession")
	if err != nil {
		log.Error(err)
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	loginSession.Values["username"] = u.Username
	//check if 2fa validity has passed
	if client != "" {
		l2faMgr := organizationdb.NewLast2FAManager(request)
		if l2faMgr.Exists(client, u.Username) {
			timestamp, err := l2faMgr.GetLast2FA(client, u.Username)
			if err != nil {
				log.Error(err)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
			mgr := organizationdb.NewManager(request)
			seconds, err := mgr.GetValidity(client)
			if err != nil {
				log.Error(err)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
			timeconverted := time.Time(timestamp)
			if timeconverted.Add(time.Second * time.Duration(seconds)).After(time.Now()) {
				service.loginUser(w, request, u.Username)
				return
			}
		}
	}

	sessions.Save(request, w)
	w.WriteHeader(http.StatusNoContent)
}
コード例 #20
0
func (api OrganizationsAPI) UpdateOrganizationOrgMemberShip(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	body := struct {
		Org  string
		Role string
	}{}

	if err := json.NewDecoder(r.Body).Decode(&body); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgMgr := organization.NewManager(r)
	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "updating organization membership", err)
		}
		return
	}

	if !orgMgr.Exists(body.Org) {
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}

	// check if the authenticated user is an owner of the Org
	// the user is known to be an owner of the first organization since we've required the organization:owner scope
	authenticateduser := context.Get(r, "authenticateduser").(string)
	isOwner, err := orgMgr.IsOwner(body.Org, authenticateduser)
	if err != nil {
		log.Error("Error while checking if user is owner of an organization: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if !isOwner {
		http.Error(w, http.StatusText(http.StatusForbidden), http.StatusForbidden)
		return
	}

	var oldRole string
	for _, v := range org.OrgMembers {
		if v == body.Org {
			oldRole = "orgmembers"
		}
	}
	for _, v := range org.OrgOwners {
		if v == body.Org {
			oldRole = "orgowners"
		}
	}
	if body.Role == "members" {
		body.Role = "orgmembers"
	} else {
		body.Role = "orgowners"
	}
	err = orgMgr.UpdateOrgMembership(globalid, body.Org, oldRole, body.Role)
	if err != nil {
		handleServerError(w, "updating organizations membership in another org", err)
		return
	}
	org, err = orgMgr.GetByName(globalid)
	if err != nil {
		handleServerError(w, "getting organization", err)
	}
	json.NewEncoder(w).Encode(org)

}
コード例 #21
0
// Handler return HTTP handler representation of this middleware
func (om *Oauth2oauth_2_0Middleware) Handler(next http.Handler) http.Handler {
	return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {

		var scopes []string
		protectedOrganization := mux.Vars(r)["globalid"]
		var atscopestring string
		var username string
		var clientID string
		var globalID string

		accessToken := om.GetAccessToken(r)
		if accessToken != "" {
			//TODO: cache
			oauthMgr := oauthservice.NewManager(r)
			at, err := oauthMgr.GetAccessToken(accessToken)
			if err != nil {
				log.Error(err)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}
			if at == nil {
				http.Error(w, http.StatusText(http.StatusUnauthorized), http.StatusUnauthorized)
				return
			}
			globalID = at.GlobalID
			username = at.Username
			atscopestring = at.Scope
			clientID = at.ClientID
		} else {
			if webuser, ok := context.GetOk(r, "webuser"); ok {
				if parsedusername, ok := webuser.(string); ok && parsedusername != "" {
					username = parsedusername
					atscopestring = "admin"
					clientID = itsyouonlineClientID
				}
			}
		}
		if (username == "" && globalID == "") || clientID == "" {
			http.Error(w, http.StatusText(http.StatusUnauthorized), http.StatusUnauthorized)
			return
		}

		context.Set(r, "authenticateduser", username)
		//If the authorized organization is the protected organization itself or is a parent of it
		if len(globalID) > 0 && (globalID == protectedOrganization || strings.HasPrefix(protectedOrganization, globalID+".")) {
			scopes = []string{atscopestring}
		} else {
			orgMgr := organization.NewManager(r)
			isOwner, err := orgMgr.IsOwner(protectedOrganization, username)
			if err != nil {
				log.Error(err)
				http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
				return
			}

			if isOwner && ((clientID == itsyouonlineClientID && atscopestring == "admin") || scopeStringContainsScope(atscopestring, "user:admin")) {
				scopes = []string{"organization:owner"}
			} else {
				isMember, err := orgMgr.IsMember(protectedOrganization, username)
				if err != nil {
					log.Error(err)
					http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
					return
				}
				if isMember && ((clientID == itsyouonlineClientID && atscopestring == "admin") || scopeStringContainsScope(atscopestring, "user:admin")) {
					scopes = []string{"organization:member"}
				}
			}
		}

		//TODO: scopes "organization:info", "organization:contracts:read"

		log.Debug("Available scopes: ", scopes)

		// check scopes
		if !om.CheckScopes(scopes) {
			w.WriteHeader(403)
			return
		}

		next.ServeHTTP(w, r)
	})
}
コード例 #22
0
// AddOrganizationMember Assign a member to organization
// It is handler for POST /organizations/{globalid}/members
func (api OrganizationsAPI) AddOrganizationMember(w http.ResponseWriter, r *http.Request) {
	globalid := mux.Vars(r)["globalid"]

	var s searchMember

	if err := json.NewDecoder(r.Body).Decode(&s); err != nil {
		http.Error(w, http.StatusText(http.StatusBadRequest), http.StatusBadRequest)
		return
	}

	orgMgr := organization.NewManager(r)

	org, err := orgMgr.GetByName(globalid)
	if err != nil {
		if err == mgo.ErrNotFound {
			http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		} else {
			handleServerError(w, "getting organization", err)
		}
		return
	}

	// Check if user exists
	u, err := SearchUser(r, s.SearchString)
	if err != nil {
		if err != mgo.ErrNotFound {
			log.Error(err)
			http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
			return
		}
		http.Error(w, http.StatusText(http.StatusNotFound), http.StatusNotFound)
		return
	}
	for _, membername := range org.Members {
		if membername == u.Username {
			http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
			return
		}
	}

	for _, membername := range org.Owners {
		if membername == u.Username {
			http.Error(w, http.StatusText(http.StatusConflict), http.StatusConflict)
			return
		}
	}

	// Create JoinRequest
	invitationMgr := invitations.NewInvitationManager(r)
	count, err := invitationMgr.CountByOrganization(globalid)
	if err != nil {
		log.Error(err)
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}
	if count >= MAX_AMOUNT_INVITATIONS_PER_ORGANIZATION {
		log.Error("Reached invitation limit for organization ", globalid)
		writeErrorResponse(w, 422, "max_amount_of_invitations_reached")
		return
	}
	orgReq := &invitations.JoinOrganizationInvitation{
		Role:         invitations.RoleMember,
		Organization: globalid,
		User:         u.Username,
		Status:       invitations.RequestPending,
		Created:      db.DateTime(time.Now()),
	}

	if err := invitationMgr.Save(orgReq); err != nil {
		log.Error("Error inviting member: ", err.Error())
		http.Error(w, http.StatusText(http.StatusInternalServerError), http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	w.WriteHeader(http.StatusCreated)

	json.NewEncoder(w).Encode(orgReq)
}