Example #1
0
// Put updates a device
func Put(render render.Render, r doorbot.Repositories, params martini.Params, vm DeviceViewModel) {
	id, err := strconv.ParseUint(params["id"], 10, 32)
	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.DeviceRepository()
	device, err := repo.Find(r.DB(), uint(id))
	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"device_id":  id,
			"step":       "device-find",
		}).Error("Api::Devices->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if device == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified device does not exists"}))
		return
	}

	device.Name = vm.Device.Name
	device.DeviceID = vm.Device.DeviceID
	device.Make = vm.Device.Make
	device.Description = vm.Device.Description
	device.IsEnabled = vm.Device.IsEnabled

	_, err = repo.Update(r.DB(), device)

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"device_id":  id,
			"step":       "device-update",
		}).Error("Api::Devices->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	log.WithFields(log.Fields{
		"account_id": r.AccountScope(),
		"device_id":  id,
	}).Info("Api::Devices->Put device updated")

	vm.Device = device

	render.JSON(http.StatusOK, vm)
}
Example #2
0
// Get return a specific account
func Get(render render.Render, r doorbot.Repositories, params martini.Params, session *auth.Authorization) {
	id, err := strconv.ParseUint(params["id"], 10, 32)

	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.AccountRepository()

	account, err := repo.Find(r.DB(), uint(id))

	if err != nil {
		log.WithFields(log.Fields{
			"account_id": id,
			"error":      err,
		}).Error("Api::Accounts->Get database error.")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if account == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{}))
		return
	}

	// Switch the view model depending on who/what requests the information.
	switch session.Type {
	case auth.AuthorizationAdministrator:
		render.JSON(http.StatusOK, AccountViewModel{Account: account})
	case auth.AuthorizationPerson:
		if session.Person.IsAccountManager() {
			render.JSON(http.StatusOK, AccountViewModel{Account: account})
			return
		}

		// Display a reduced version of the account.
		public := PublicAccount{
			ID:   account.ID,
			Name: account.Name,
			Host: account.Host,
		}

		render.JSON(http.StatusOK, PublicAccountViewModel{Account: public})
	default:
		render.Status(http.StatusForbidden)
		return
	}
}
Example #3
0
// Put updates a door
func Put(render render.Render, r doorbot.Repositories, params martini.Params, vm DoorViewModel) {
	id, err := strconv.ParseUint(params["id"], 10, 32)
	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.DoorRepository()
	door, err := repo.Find(r.DB(), uint(id))
	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"door_id":    id,
			"step":       "door-find",
		}).Error("Api::Doors->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if door == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified door does not exists"}))
		return
	}

	door.Name = vm.Door.Name

	_, err = repo.Update(r.DB(), door)

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"door_id":    id,
			"step":       "door-update",
		}).Error("Api::Doors->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	log.WithFields(log.Fields{
		"account_id": r.AccountScope(),
		"door_id":    vm.Door.ID,
	}).Error("Api::Doors->Post door updated")

	render.JSON(http.StatusOK, DoorViewModel{Door: door})
}
Example #4
0
// Disable a device
func Disable(render render.Render, r doorbot.Repositories, params martini.Params) {
	id, err := strconv.ParseUint(params["id"], 10, 32)

	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"the id must be an unsigned integer"}))
		return
	}

	repo := r.DeviceRepository()
	device, err := repo.Find(r.DB(), uint(id))
	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"device_id":  id,
			"step":       "device-find",
		}).Error("Api::Devices->Disable database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if device == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified deevice does not exists."}))
		return
	}

	_, err = repo.Enable(r.DB(), device, false)

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"device_id":  id,
			"step":       "device-disable",
		}).Error("Api::Devices->Disable database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	log.WithFields(log.Fields{
		"account_id": r.AccountScope(),
		"device_id":  id,
	}).Info("Api::Devices->Disabled device disabled")

	render.Status(http.StatusNoContent)
}
Example #5
0
func TestDeleteInvalidID(t *testing.T) {
	render := new(tests.MockRender)

	repositories := new(tests.MockRepositories)

	params := martini.Params{
		"id": "help",
	}

	render.On("JSON", http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"})).Return()

	Delete(render, repositories, params)

	render.Mock.AssertExpectations(t)
	repositories.Mock.AssertExpectations(t)
}
Example #6
0
// Get a specific person
func Get(render render.Render, r doorbot.Repositories, params martini.Params, session *auth.Authorization) {
	id, err := strconv.ParseUint(params["id"], 10, 32)

	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.PersonRepository()
	person, err := repo.Find(r.DB(), uint(id))

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"person_id":  id,
		}).Error("Api::People->Get database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if person == nil {
		err := doorbot.NewEntityNotFoundResponse([]string{"The specified person does not exists"})
		render.JSON(http.StatusNotFound, err)
		return
	}

	switch session.Type {
	case auth.AuthorizationAdministrator:
		render.JSON(http.StatusOK, PersonViewModel{Person: person})

	case auth.AuthorizationDevice:
		render.JSON(http.StatusOK, PublicPersonViewModel{Person: newPublicPerson(person)})

	case auth.AuthorizationPerson:
		// Display detailed info if the requesting user is an account manager or it is the same person
		if session.Person.IsAccountManager() || session.Person.ID == person.ID {
			render.JSON(http.StatusOK, PersonViewModel{Person: person})
			return
		}

		render.JSON(http.StatusOK, PublicPersonViewModel{Person: newPublicPerson(person)})
	default:
		render.Status(http.StatusForbidden)
	}
}
Example #7
0
// Delete an account ( admin panel )
func Delete(render render.Render, r doorbot.Repositories, params martini.Params, administrator *doorbot.Administrator) {
	id, err := strconv.ParseUint(params["id"], 10, 32)

	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.AccountRepository()

	account, err := repo.Find(r.DB(), uint(id))
	if err != nil {
		log.WithFields(log.Fields{
			"error":            err.Error(),
			"account_id":       account.ID,
			"administrator_id": administrator.ID,
		}).Error("Api::Accounts->Delete database find error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if account == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified account does not exists."}))
		return
	}

	_, err = repo.Delete(r.DB(), account)

	if err != nil {
		log.WithFields(log.Fields{
			"error":            err.Error(),
			"administrator_id": administrator.ID,
			"account_id":       account.ID,
		}).Error("Api::Accounts->Delete database delete error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	log.WithFields(log.Fields{
		"administrator_id": administrator.ID,
		"account_id":       account.ID,
	}).Info("Api::Accounts->Delete account deleted by administrator.")

	render.Status(http.StatusNoContent)
}
Example #8
0
func TestPutInvalidID(t *testing.T) {
	render := new(tests.MockRender)

	repositories := new(tests.MockRepositories)

	params := martini.Params{
		"id": "help",
	}

	postDoor := &doorbot.Door{
		Name: "Chicken Nick",
	}

	render.On("JSON", http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"})).Return()

	Put(render, repositories, params, DoorViewModel{Door: postDoor})

	render.Mock.AssertExpectations(t)
	repositories.Mock.AssertExpectations(t)
}
Example #9
0
func TestGetParseIntError(t *testing.T) {

	render := new(tests.MockRender)
	repo := new(tests.MockAccountRepository)

	repositories := new(tests.MockRepositories)
	repositories.On("AccountRepository").Return(repo)

	session := &auth.Authorization{}

	params := martini.Params{
		"id": "help",
	}

	render.On("JSON", http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"})).Return()

	Get(render, repositories, params, session)

	render.Mock.AssertExpectations(t)
	repo.Mock.AssertExpectations(t)
}
Example #10
0
// Get return a specific door
func Get(render render.Render, r doorbot.Repositories, params martini.Params) {
	id, err := strconv.ParseUint(params["id"], 10, 32)

	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	repo := r.DoorRepository()
	door, err := repo.Find(r.DB(), uint(id))

	if door == nil || err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"door_id":    id,
		}).Error("Api::Doors->Get database error")

		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified door does not exists"}))
		return
	}

	render.JSON(http.StatusOK, DoorViewModel{Door: door})
}
Example #11
0
func TestDeleteInvalidID(t *testing.T) {
	render := new(tests.MockRender)

	repositories := new(tests.MockRepositories)

	params := martini.Params{
		"id": "help",
	}

	account := &doorbot.Account{}
	session := &auth.Authorization{
		Type: auth.AuthorizationPerson,
		Person: &doorbot.Person{
			AccountType: doorbot.AccountOwner,
		},
	}

	render.On("JSON", http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"})).Return()

	Delete(render, repositories, params, account, session)

	render.Mock.AssertExpectations(t)
	repositories.Mock.AssertExpectations(t)
}
Example #12
0
// Delete a person
func Delete(render render.Render, r doorbot.Repositories, params martini.Params, a *doorbot.Account, session *auth.Authorization) {
	id, err := strconv.ParseUint(params["id"], 10, 32)
	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	var logFields log.Fields
	var logMessage string

	switch session.Type {
	case auth.AuthorizationAdministrator:
		logFields = log.Fields{
			"account_id":      r.AccountScope(),
			"person_id":       id,
			"admnistrator_id": session.Administrator.ID,
		}
		logMessage = "Api::People->Delete user deleted by administrator"

	case auth.AuthorizationPerson:
		if !session.Person.IsAccountManager() {
			log.WithFields(log.Fields{
				"account_id":        r.AccountScope(),
				"person_id":         id,
				"request_person_id": session.Person.ID,
			}).Warn("Api::People->Delete forbidden")

			render.Status(http.StatusForbidden)
			return
		}

		logFields = log.Fields{
			"account_id":     r.AccountScope(),
			"person_id":      id,
			"modified_by_id": session.Person.ID,
		}

		logMessage = "Api::People->Put user deleted by user"

	default:
		log.WithFields(log.Fields{
			"account_id":        r.AccountScope(),
			"person_id":         id,
			"request_person_id": session.Person.ID,
		}).Warn("Api::People->Delete forbidden")

		render.Status(http.StatusForbidden)
		return
	}

	repo := r.PersonRepository()
	person, err := repo.Find(r.DB(), uint(id))

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"person_id":  person.ID,
			"step":       "person-find",
		}).Error("Api::People->Delete database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if person == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified person does not exists"}))
		return
	}

	_, err = repo.Delete(r.DB(), person)

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"person_id":  person.ID,
			"step":       "person-delete",
		}).Error("Api::People->Delete database error")

		render.Status(http.StatusInternalServerError)
		return
	}

	log.WithFields(logFields).Info(logMessage)

	render.Status(http.StatusNoContent)
}
Example #13
0
// Put updates a person
func Put(render render.Render, r doorbot.Repositories, params martini.Params, vm PersonViewModel, session *auth.Authorization) {
	id, err := strconv.ParseUint(params["id"], 10, 32)
	if err != nil {
		render.JSON(http.StatusBadRequest, doorbot.NewBadRequestErrorResponse([]string{"The id must be an unsigned integer"}))
		return
	}

	var logFields log.Fields
	var logMessage string
	canUpdateAccountType := false

	switch session.Type {
	case auth.AuthorizationAdministrator:
		logFields = log.Fields{
			"account_id":      r.AccountScope(),
			"person_id":       id,
			"admnistrator_id": session.Administrator.ID,
		}
		logMessage = "Api::People->Put user updated by administrator"

		canUpdateAccountType = true

	case auth.AuthorizationPerson:
		if uint(id) != session.Person.ID {
			if session.Person.IsAccountManager() {
				canUpdateAccountType = true
			} else {
				log.WithFields(log.Fields{
					"account_id":        r.AccountScope(),
					"person_id":         id,
					"request_person_id": session.Person.ID,
				}).Warn("Api::People->Delete forbidden")

				render.Status(http.StatusForbidden)
				return
			}
		}

		logFields = log.Fields{
			"account_id":        r.AccountScope(),
			"person_id":         id,
			"request_person_id": session.Person.ID,
		}

		logMessage = "Api::People->Put user updated by user"

	default:
		log.WithFields(log.Fields{
			"account_id":        r.AccountScope(),
			"person_id":         id,
			"request_person_id": session.Person.ID,
		}).Warn("Api::People->Put forbidden")

		render.Status(http.StatusForbidden)
		return
	}

	repo := r.PersonRepository()
	person, err := repo.Find(r.DB(), uint(id))

	if err != nil {
		log.WithFields(log.Fields{
			"error":      err,
			"account_id": r.AccountScope(),
			"person_id":  id,
			"step":       "person-find",
		}).Error("Api::People->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	if person == nil {
		render.JSON(http.StatusNotFound, doorbot.NewEntityNotFoundResponse([]string{"The specified person does not exists"}))
		return
	}

	person.Name = vm.Person.Name
	person.Email = vm.Person.Email
	person.PhoneNumber = vm.Person.PhoneNumber
	person.Title = vm.Person.Title
	person.IsVisible = vm.Person.IsVisible
	person.IsAvailable = vm.Person.IsAvailable
	person.NotificationsEnabled = vm.Person.NotificationsEnabled
	person.NotificationsAppEnabled = vm.Person.NotificationsAppEnabled
	person.NotificationsChatEnabled = vm.Person.NotificationsChatEnabled
	person.NotificationsEmailEnabled = vm.Person.NotificationsEmailEnabled
	person.NotificationsSMSEnabled = vm.Person.NotificationsSMSEnabled

	if canUpdateAccountType {
		person.AccountType = vm.Person.AccountType
	}

	_, err = repo.Update(r.DB(), person)

	if err != nil {
		log.WithFields(log.Fields{
			"error":             err,
			"account_id":        r.AccountScope(),
			"person_id":         person.ID,
			"request_person_id": session.Person.ID,
			"step":              "person-update",
		}).Error("Api::People->Put database error")

		render.JSON(http.StatusInternalServerError, doorbot.NewInternalServerErrorResponse([]string{}))
		return
	}

	vm.Person = person

	log.WithFields(logFields).Info(logMessage)

	render.JSON(http.StatusOK, vm)
}