Niveles de permisos de usuario en una API RESTful

23

Digamos que tengo una compañía que clasifica a los gatos más lindos en Internet.

Ofrezco un recurso en el/cats/ que proporciona a los usuarios los últimos y adorables gatos adorables.

Los usuarios pueden obtener solo los 3 gatos principales si no han pagado en absoluto o no se han registrado. Los 10 gatos principales si pagaron 337 dólares y están conectados, y los 100 gatos principales si pagaron 1337 dólares y están conectados. Tengo un 'identificador de usuario' al hacer la solicitud.

En resumen, los consumidores /cats/obtienen un número diferente de gatos según su 'clasificación de usuarios' . Tengo un identificador de usuario en el extremo consumidor, pero no tengo una representación explícita del nivel de usuario en el extremo consumidor. Me gustaría informar a los usuarios que pueden actualizar su suscripción al hacer la solicitud. Es decir, necesito distinguir entre 3 gatos, ya que solo ofrezco 3 gatos y 3 gatos porque eso es lo que permite el nivel de usuario .

¿Cuál es la mejor práctica para distinguir la limitación del recurso porque el consumidor no tiene privilegios suficientes y limitarlo porque eso es lo que tiene el consumidor?

¿Cómo sabe el cliente si puede actualizar su clasificación? Es decir, que sólo tiene un recurso limitado, ya que no tienen permisos. ¿Cuál es la mejor práctica aquí?

Tenga en cuenta que esta es una simplificación general del caso real. Además, solo para aclarar: se aprecia la lectura.


Actualizar:

Aquí hay opciones que hemos considerado:

  • Almacenar los objetos de permisos de usuario una vez en el cliente, buscándolo solo cuando se realiza el inicio de sesión o la actualización de la cuenta.
  • Pasando nullvalores en JSON que indican que existe, pero no se transfirió nada real . Entonces 10 gatos para un usuario con 3 gatos podrían ser["Garfield","Sylvester","Puss in Boots",null*7]
  • Pasar un par de permisos de recursos {cats:["Whiskers","Fluffy","Socks"],authCount:3}

Me gustaría hacer esto bien la primera vez para entregar los gatos más lindos de la mejor manera posible y nos gustaría y nos gustaría

Benjamin Gruenbaum
fuente
44
ahora quiero ver fotos de gatos lindos
Carrie Kendall
No lo entiendo Si no almacena el 'nivel de usuario' en ningún lado, entonces no puede distinguir. Parece que tampoco tiene ninguna información de usuario almacenada en el servidor, por lo que no puede almacenar su nivel de usuario con ella.
Jan Doggen
@ JanDoggen Tengo el nivel de usuario en el servidor (el cliente transmite el identificador al servidor).
Benjamin Gruenbaum
¿Ayuda? ¿No obtengo la referencia 1337?
Marjan Venema
Leet
JustinC

Respuestas:

18

Yo diría que depende de tu audiencia.

No-dev

Si su audiencia no es la de un desarrollador, seguiría la siguiente manera:

Digamos que devuelve JSON por el bien del ejemplo.

GET /cats HTTP/1.1

{
    "cats": [
        "Can I haz cheeseburger",
        "If it fits, I sits",
        "It's caturday!"
    ],
    "permissions": {
        "level": "free",
        "information": "You have access to 3 cats. Upgrade to ... to get 10 cats!"
    }
}

O algo similar.

Es informativo para el usuario saber cuál es el estado de su cuenta, y le permite poner cualquier información que desee, como un mensaje de marketing. El punto más importante de esta manera es darles una visibilidad fácil a sus usuarios de su cuenta corriente.

Dev

Sin embargo, si su audiencia es puramente desarrolladores, entonces yo diría: vaya con la forma completa compatible con HTTP. Para almacenar los metadatos, utiliza encabezados HTTP.

Aquí hay un ejemplo:

GET /cats HTTP/1.1

X-Account: anonymous
X-Account-Possible-Upgrades: 2
X-Account-Limit: 3

Luego, proporcione una documentación clara de lo que significan estos encabezados. La mayoría de los desarrolladores irán directamente a la documentación cuando vean estos encabezados personalizados, especialmente si están viendo un límite. Puede ir aún más lejos y mostrar el enlace en los encabezados. O puede mostrar un enlace a la página de precios.

X-Account-Doc: http://your/doc

Pero, de nuevo, muchos desarrolladores no saben cómo funciona HTTP.

Entonces es tu decisión

Uno es más correcto, el otro es más accesible.

Misceláneos

Algunas otras cosas diversas relacionadas con su pregunta:

Florian Margaine
fuente
1
Sí, esto tiene sentido absoluto, aunque como nota al margen, encuentro que parte de la información de autenticación (ent / orize) que va en los encabezados HTTP es un enfoque apropiado, ya que es efectivamente metadato.
Jimmy Hoffa
@JimmyHoffa De hecho, son metadatos, y mi primer pensamiento fue usar los encabezados HTTP. Sin embargo, en este caso, los encabezados HTTP no ofrecen suficiente visibilidad para el cliente y la granularidad necesaria para los mensajes de marketing. (Editó la respuesta para agregar este detalle.)
Florian Margaine
@JimmyHoffa ¿cómo? Un 402 no servirá en este caso. ¿Que sugieres?
Benjamin Gruenbaum
@BenjaminGruenbaum No dije códigos de respuesta, dije encabezados; puede agregar todos los encabezados personalizados que desee para los metadatos, sería prudente que todas las respuestas de una API relajante solo tengan el rol de usuario en el encabezado como UserRole = level1o como desee llamarlo para asegurarse de que los consumidores siempre sepan cómo presente cualquier información que reciba, y es coherente en todas las respuestas donde los modelos de datos que regresan serán diferentes de una solicitud a otra, los consumidores siempre pueden verificar su función de la misma manera.
Jimmy Hoffa
1
@BenjaminGruenbaum He reescrito completamente la respuesta.
Florian Margaine
4

¿Cómo sabe el cliente si puede actualizar su clasificación?

Eso depende del cliente. Normalmente, puede colocar dicha información en forma de mensaje de texto hipotexto (también conocido como HTML) en el cuerpo de respuesta del método REST. Sin embargo, eso solo tiene sentido si la API REST se usa con un cliente HTML.

Similar para XML y JSON.


Editar: puede confundir el uso de una API (expandir este acrónimo) con la comercialización de sus tipos de cuenta / planes de usuario. No mezclaría esto, ya que siempre se vuelve sospechoso (las decisiones comerciales pueden requerir cambios más rápidos que los cambios en el software para comunicar diferentes respuestas debido a que estos cambios pueden llegar al plato a tiempo).

En cambio, informe a sus usuarios a través de un canal diferente, por ejemplo, con el boletín de noticias, cuáles son sus beneficios.

Esto funciona particularmente bien cuando la persona que se suscribe al servicio no es la que está programando contra la API. Por ejemplo:

George (que es un chico orgullosamente gay a la edad de 36 gatitos cariñosos) compra acceso a cute-cats-4-me.com y le dice a su cónyuge de 16 años (que está bien con los sistemas informáticos de secuencias de comandos, incluido Linux) que cree un aplicación de señalización digital que muestra lindos gatitos lindos en la pared del apartamento.

Entonces, el tipo que se está divirtiendo programando esto en realidad no es el destinatario más directo de la información.

Alternativamente, en respuesta al inicio de sesión y un método de información del usuario, proporcione todos los detalles sangrientos.

Pero cuando un usuario solicita gatos mediante programación, ya debe saber por qué solo recupera tres gatos o más. Pero no resuelve este problema de comunicación con el código.

De lo contrario, permítales consultar más y luego devolver un aviso de falla si sus derechos no son suficientes. Pero, de nuevo, ese no es un software fácil de usar.

hakre
fuente
1
@ Racheet: ¿Tienes algún problema cuando las chicas tienen el dinero en la casa y les dicen a los chicos qué hacer?
hakre
1
Tengo un problema con un ejemplo que afirma que las niñas necesitan novios para programarlas.
Racheet