mirror of
https://github.com/OpenBankProject/OBP-API.git
synced 2026-02-06 15:06:50 +00:00
Merge branch 'OpenBankProject:develop' into develop
This commit is contained in:
commit
d852d59e3e
@ -40,7 +40,7 @@ import code.util.Helper
|
||||
import code.util.Helper.{MdcLoggable, ObpS, SILENCE_IS_GOLDEN}
|
||||
import code.views.Views
|
||||
import code.views.system.ViewDefinition
|
||||
import code.webuiprops.{MappedWebUiPropsProvider, WebUiPropsCommons}
|
||||
import code.webuiprops.{MappedWebUiPropsProvider, WebUiPropsCommons, WebUiPropsPutJsonV600}
|
||||
import code.dynamicEntity.DynamicEntityCommons
|
||||
import code.DynamicData.{DynamicData, DynamicDataProvider}
|
||||
import com.github.dwickern.macros.NameOf.nameOf
|
||||
@ -3634,6 +3634,181 @@ trait APIMethods600 {
|
||||
}
|
||||
}
|
||||
|
||||
staticResourceDocs += ResourceDoc(
|
||||
createOrUpdateWebUiProps,
|
||||
implementedInApiVersion,
|
||||
nameOf(createOrUpdateWebUiProps),
|
||||
"PUT",
|
||||
"/management/webui_props/WEBUI_PROP_NAME",
|
||||
"Create or Update WebUiProps",
|
||||
s"""Create or Update a WebUiProps.
|
||||
|
|
||||
|${userAuthenticationMessage(true)}
|
||||
|
|
||||
|This endpoint is idempotent - it will create the property if it doesn't exist, or update it if it does.
|
||||
|The property is identified by WEBUI_PROP_NAME in the URL path.
|
||||
|
|
||||
|Explanation of Fields:
|
||||
|
|
||||
|* WEBUI_PROP_NAME in URL path (must start with `webui_`, contain only alphanumeric characters, underscore, and dot, not exceed 255 characters, and will be converted to lowercase)
|
||||
|* value is required String value in request body
|
||||
|
|
||||
|The line break and double quotations should be escaped, example:
|
||||
|
|
||||
|```
|
||||
|
|
||||
|{"name": "webui_some", "value": "this value
|
||||
|have "line break" and double quotations."}
|
||||
|
|
||||
|```
|
||||
|should be escaped like this:
|
||||
|
|
||||
|```
|
||||
|
|
||||
|{"name": "webui_some", "value": "this value\\nhave \\"line break\\" and double quotations."}
|
||||
|
|
||||
|```
|
||||
|
|
||||
|Insert image examples:
|
||||
|
|
||||
|```
|
||||
|// set width=100 and height=50
|
||||
|{"name": "webui_some_pic", "value": "here is a picture "}
|
||||
|
|
||||
|// only set height=50
|
||||
|{"name": "webui_some_pic", "value": "here is a picture "}
|
||||
|
|
||||
|// only width=20%
|
||||
|{"name": "webui_some_pic", "value": "here is a picture "}
|
||||
|
|
||||
|```
|
||||
|
|
||||
|""",
|
||||
WebUiPropsPutJsonV600("https://apiexplorer.openbankproject.com"),
|
||||
WebUiPropsCommons("webui_api_explorer_url", "https://apiexplorer.openbankproject.com", Some("some-web-ui-props-id")),
|
||||
List(
|
||||
UserNotLoggedIn,
|
||||
UserHasMissingRoles,
|
||||
InvalidJsonFormat,
|
||||
InvalidWebUiProps,
|
||||
UnknownError
|
||||
),
|
||||
List(apiTagWebUiProps),
|
||||
Some(List(canCreateWebUiProps))
|
||||
)
|
||||
|
||||
lazy val createOrUpdateWebUiProps: OBPEndpoint = {
|
||||
case "management" :: "webui_props" :: webUiPropName :: Nil JsonPut json -> _ => {
|
||||
cc => implicit val ec = EndpointContext(Some(cc))
|
||||
for {
|
||||
(Full(u), callContext) <- authenticatedAccess(cc)
|
||||
_ <- NewStyle.function.hasEntitlement("", u.userId, canCreateWebUiProps, callContext)
|
||||
// Convert name to lowercase
|
||||
webUiPropNameLower = webUiPropName.toLowerCase
|
||||
invalidMsg = s"""$InvalidWebUiProps name must start with webui_, but current name is: ${webUiPropNameLower} """
|
||||
_ <- NewStyle.function.tryons(invalidMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.startsWith("webui_"))
|
||||
}
|
||||
invalidCharsMsg = s"""$InvalidWebUiProps name must contain only alphanumeric characters, underscore, and dot. Current name: ${webUiPropNameLower} """
|
||||
_ <- NewStyle.function.tryons(invalidCharsMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.matches("^[a-zA-Z0-9_.]+$"))
|
||||
}
|
||||
invalidLengthMsg = s"""$InvalidWebUiProps name must not exceed 255 characters. Current length: ${webUiPropNameLower.length} """
|
||||
_ <- NewStyle.function.tryons(invalidLengthMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.length <= 255)
|
||||
}
|
||||
// Check if resource already exists to determine status code
|
||||
existingProp <- Future { MappedWebUiPropsProvider.getByName(webUiPropNameLower) }
|
||||
resourceExists = existingProp.isDefined
|
||||
failMsg = s"$InvalidJsonFormat The Json body should contain a value field"
|
||||
valueJson <- NewStyle.function.tryons(failMsg, 400, callContext) {
|
||||
json.extract[WebUiPropsPutJsonV600]
|
||||
}
|
||||
webUiPropsData = WebUiPropsCommons(webUiPropNameLower, valueJson.value)
|
||||
Full(webUiProps) <- Future { MappedWebUiPropsProvider.createOrUpdate(webUiPropsData) }
|
||||
} yield {
|
||||
val commonsData: WebUiPropsCommons = webUiProps
|
||||
val statusCode = if (resourceExists) HttpCode.`200`(callContext) else HttpCode.`201`(callContext)
|
||||
(commonsData, statusCode)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
staticResourceDocs += ResourceDoc(
|
||||
deleteWebUiProps,
|
||||
implementedInApiVersion,
|
||||
nameOf(deleteWebUiProps),
|
||||
"DELETE",
|
||||
"/management/webui_props/WEBUI_PROP_NAME",
|
||||
"Delete WebUiProps",
|
||||
s"""Delete a WebUiProps specified by WEBUI_PROP_NAME.
|
||||
|
|
||||
|${userAuthenticationMessage(true)}
|
||||
|
|
||||
|The property name will be converted to lowercase before deletion.
|
||||
|
|
||||
|Returns 204 No Content on successful deletion.
|
||||
|
|
||||
|This endpoint is idempotent - if the property does not exist, it still returns 204 No Content.
|
||||
|
|
||||
|Requires the $canDeleteWebUiProps role.
|
||||
|
|
||||
|""",
|
||||
EmptyBody,
|
||||
EmptyBody,
|
||||
List(
|
||||
UserNotLoggedIn,
|
||||
UserHasMissingRoles,
|
||||
InvalidWebUiProps,
|
||||
UnknownError
|
||||
),
|
||||
List(apiTagWebUiProps),
|
||||
Some(List(canDeleteWebUiProps))
|
||||
)
|
||||
|
||||
lazy val deleteWebUiProps: OBPEndpoint = {
|
||||
case "management" :: "webui_props" :: webUiPropName :: Nil JsonDelete _ => {
|
||||
cc => implicit val ec = EndpointContext(Some(cc))
|
||||
for {
|
||||
(Full(u), callContext) <- authenticatedAccess(cc)
|
||||
_ <- NewStyle.function.hasEntitlement("", u.userId, canDeleteWebUiProps, callContext)
|
||||
// Convert name to lowercase
|
||||
webUiPropNameLower = webUiPropName.toLowerCase
|
||||
invalidMsg = s"""$InvalidWebUiProps name must start with webui_, but current name is: ${webUiPropNameLower} """
|
||||
_ <- NewStyle.function.tryons(invalidMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.startsWith("webui_"))
|
||||
}
|
||||
invalidCharsMsg = s"""$InvalidWebUiProps name must contain only alphanumeric characters, underscore, and dot. Current name: ${webUiPropNameLower} """
|
||||
_ <- NewStyle.function.tryons(invalidCharsMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.matches("^[a-zA-Z0-9_.]+$"))
|
||||
}
|
||||
invalidLengthMsg = s"""$InvalidWebUiProps name must not exceed 255 characters. Current length: ${webUiPropNameLower.length} """
|
||||
_ <- NewStyle.function.tryons(invalidLengthMsg, 400, callContext) {
|
||||
require(webUiPropNameLower.length <= 255)
|
||||
}
|
||||
// Check if resource exists
|
||||
existingProp <- Future { MappedWebUiPropsProvider.getByName(webUiPropNameLower) }
|
||||
_ <- existingProp match {
|
||||
case Full(prop) =>
|
||||
// Property exists - delete it
|
||||
Future { MappedWebUiPropsProvider.delete(prop.webUiPropsId.getOrElse("")) } map {
|
||||
case Full(true) => Full(())
|
||||
case Full(false) => ObpApiFailure(s"$UnknownError Cannot delete WebUI prop", 500, callContext)
|
||||
case Empty => ObpApiFailure(s"$UnknownError Cannot delete WebUI prop", 500, callContext)
|
||||
case Failure(msg, _, _) => ObpApiFailure(msg, 500, callContext)
|
||||
}
|
||||
case Empty =>
|
||||
// Property not found - idempotent delete returns success
|
||||
Future.successful(Full(()))
|
||||
case Failure(msg, _, _) =>
|
||||
Future.failed(new Exception(msg))
|
||||
}
|
||||
} yield {
|
||||
(EmptyBody, HttpCode.`204`(callContext))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
staticResourceDocs += ResourceDoc(
|
||||
getSystemDynamicEntities,
|
||||
implementedInApiVersion,
|
||||
|
||||
@ -19,6 +19,7 @@ object MappedWebUiPropsProvider extends WebUiPropsProvider {
|
||||
|
||||
override def getAll(): List[WebUiPropsT] = WebUiProps.findAll()
|
||||
|
||||
override def getByName(name: String): Box[WebUiPropsT] = WebUiProps.find(By(WebUiProps.Name, name))
|
||||
|
||||
override def createOrUpdate(webUiProps: WebUiPropsT): Box[WebUiPropsT] = {
|
||||
WebUiProps.find(By(WebUiProps.Name, webUiProps.name))
|
||||
|
||||
@ -19,9 +19,13 @@ case class WebUiPropsCommons(name: String,
|
||||
|
||||
object WebUiPropsCommons extends Converter[WebUiPropsT, WebUiPropsCommons]
|
||||
|
||||
case class WebUiPropsPutJsonV600(value: String) extends JsonFieldReName
|
||||
|
||||
trait WebUiPropsProvider {
|
||||
def getAll(): List[WebUiPropsT]
|
||||
|
||||
def getByName(name: String): Box[WebUiPropsT]
|
||||
|
||||
def createOrUpdate(webUiProps: WebUiPropsT): Box[WebUiPropsT]
|
||||
|
||||
def delete(webUiPropsId: String):Box[Boolean]
|
||||
|
||||
@ -48,7 +48,9 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
* This is made possible by the scalatest maven plugin
|
||||
*/
|
||||
object VersionOfApi extends Tag(ApiVersion.v6_0_0.toString)
|
||||
object ApiEndpoint extends Tag(nameOf(Implementations6_0_0.getWebUiProp))
|
||||
object ApiEndpoint1 extends Tag(nameOf(Implementations6_0_0.getWebUiProp))
|
||||
object ApiEndpoint2 extends Tag(nameOf(Implementations6_0_0.createOrUpdateWebUiProps))
|
||||
object ApiEndpoint3 extends Tag(nameOf(Implementations6_0_0.deleteWebUiProps))
|
||||
|
||||
val rightEntity = WebUiPropsCommons("webui_api_explorer_url", "https://apiexplorer.openbankproject.com")
|
||||
val anotherEntity = WebUiPropsCommons("webui_api_manager_url", "https://apimanager.openbankproject.com")
|
||||
@ -57,7 +59,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
|
||||
feature("Get Single WebUiProp by Name v6.0.0") {
|
||||
|
||||
scenario("Get WebUiProp - successful case with explicit prop from database", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - successful case with explicit prop from database", VersionOfApi, ApiEndpoint1) {
|
||||
// First create a webui prop
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop")
|
||||
@ -76,7 +78,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
webUiPropJson.value should equal(rightEntity.value)
|
||||
}
|
||||
|
||||
scenario("Get WebUiProp - successful case with active=true returns explicit prop", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - successful case with active=true returns explicit prop", VersionOfApi, ApiEndpoint1) {
|
||||
// First create a webui prop
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop")
|
||||
@ -95,7 +97,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
webUiPropJson.value should equal(anotherEntity.value)
|
||||
}
|
||||
|
||||
scenario("Get WebUiProp - not found without active flag", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - not found without active flag", VersionOfApi, ApiEndpoint1) {
|
||||
When("We get a non-existent webui prop by name without active flag")
|
||||
val requestGet = (v6_0_0_Request / "webui-props" / "webui_non_existent_prop").GET
|
||||
val responseGet = makeGetRequest(requestGet)
|
||||
@ -105,7 +107,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
error.message should include(WebUiPropsNotFoundByName)
|
||||
}
|
||||
|
||||
scenario("Get WebUiProp - with active=true returns implicit prop from config", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - with active=true returns implicit prop from config", VersionOfApi, ApiEndpoint1) {
|
||||
// Test that we can get implicit props from sample.props.template when active=true
|
||||
When("We get a webui prop by name with active=true that exists in config but not in DB")
|
||||
// Use a prop that should exist in sample.props.template like webui_sandbox_introduction
|
||||
@ -118,7 +120,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
webUiPropJson.webUiPropsId should equal(Some("default"))
|
||||
}
|
||||
|
||||
scenario("Get WebUiProp - invalid active parameter", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - invalid active parameter", VersionOfApi, ApiEndpoint1) {
|
||||
When("We get a webui prop with invalid active parameter")
|
||||
val requestGet = (v6_0_0_Request / "webui-props" / "webui_api_explorer_url").GET.addQueryParameter("active", "invalid")
|
||||
val responseGet = makeGetRequest(requestGet)
|
||||
@ -128,7 +130,7 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
error.message should include(InvalidFilterParameterFormat)
|
||||
}
|
||||
|
||||
scenario("Get WebUiProp - database prop takes precedence over config prop when active=true", VersionOfApi, ApiEndpoint) {
|
||||
scenario("Get WebUiProp - database prop takes precedence over config prop when active=true", VersionOfApi, ApiEndpoint1) {
|
||||
// Create a webui prop that overrides a config value
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
val customValue = WebUiPropsCommons("webui_get_started_text", "Custom Get Started Text")
|
||||
@ -149,5 +151,327 @@ class WebUiPropsTest extends V600ServerSetup {
|
||||
webUiPropJson.webUiPropsId should not equal(Some("default"))
|
||||
}
|
||||
}
|
||||
|
||||
feature("Create or Update WebUiProp (PUT) v6.0.0") {
|
||||
|
||||
scenario("PUT WebUiProp - create new property successfully", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a new webui prop using PUT")
|
||||
val putValue = """{"value": "https://new-api-explorer.com"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_new_prop").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 201 Created")
|
||||
responsePut.code should equal(201)
|
||||
val webUiProp = responsePut.body.extract[WebUiPropsCommons]
|
||||
webUiProp.name should equal("webui_test_new_prop")
|
||||
webUiProp.value should equal("https://new-api-explorer.com")
|
||||
webUiProp.webUiPropsId.isDefined should equal(true)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - update existing property successfully", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop")
|
||||
val putValue1 = """{"value": "original value"}"""
|
||||
val requestPut1 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_update_prop").PUT <@(user1)
|
||||
val responsePut1 = makePutRequest(requestPut1, putValue1)
|
||||
Then("We should get a 201 Created")
|
||||
responsePut1.code should equal(201)
|
||||
|
||||
When("We update the same webui prop")
|
||||
val putValue2 = """{"value": "updated value"}"""
|
||||
val requestPut2 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_update_prop").PUT <@(user1)
|
||||
val responsePut2 = makePutRequest(requestPut2, putValue2)
|
||||
Then("We should get a 200 OK")
|
||||
responsePut2.code should equal(200)
|
||||
val webUiProp = responsePut2.body.extract[WebUiPropsCommons]
|
||||
webUiProp.name should equal("webui_test_update_prop")
|
||||
webUiProp.value should equal("updated value")
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - idempotent create (same value twice)", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
val putValue = """{"value": "idempotent value"}"""
|
||||
|
||||
When("We create a webui prop")
|
||||
val requestPut1 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_idempotent").PUT <@(user1)
|
||||
val responsePut1 = makePutRequest(requestPut1, putValue)
|
||||
Then("We should get a 201 Created")
|
||||
responsePut1.code should equal(201)
|
||||
val webUiPropsId1 = responsePut1.body.extract[WebUiPropsCommons].webUiPropsId
|
||||
|
||||
When("We PUT the same value again")
|
||||
val requestPut2 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_idempotent").PUT <@(user1)
|
||||
val responsePut2 = makePutRequest(requestPut2, putValue)
|
||||
Then("We should get a 200 OK with same ID")
|
||||
responsePut2.code should equal(200)
|
||||
val webUiPropsId2 = responsePut2.body.extract[WebUiPropsCommons].webUiPropsId
|
||||
webUiPropsId1 should equal(webUiPropsId2)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - name converted to lowercase", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop with UPPERCASE name")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "WEBUI_UPPERCASE_TEST").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 201 and name should be lowercase")
|
||||
responsePut.code should equal(201)
|
||||
val webUiProp = responsePut.body.extract[WebUiPropsCommons]
|
||||
webUiProp.name should equal("webui_uppercase_test")
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - dot allowed in name", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop with dots in name")
|
||||
val putValue = """{"value": "https://api.v1.example.com"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_api.v1.endpoint").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 201")
|
||||
responsePut.code should equal(201)
|
||||
val webUiProp = responsePut.body.extract[WebUiPropsCommons]
|
||||
webUiProp.name should equal("webui_api.v1.endpoint")
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail without webui_ prefix", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop without webui_ prefix")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "invalid_name").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 400")
|
||||
responsePut.code should equal(400)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
error.message should include("must start with webui_")
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail with hyphen in name", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop with hyphen")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_api-explorer").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 400")
|
||||
responsePut.code should equal(400)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
error.message should include("alphanumeric characters, underscore, and dot")
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail with space in name", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop with space")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_invalid name").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 400")
|
||||
responsePut.code should equal(400)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail without authentication", VersionOfApi, ApiEndpoint2) {
|
||||
When("We try to PUT without authentication")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_noauth").PUT
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 401")
|
||||
responsePut.code should equal(401)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail without CanCreateWebUiProps role", VersionOfApi, ApiEndpoint2) {
|
||||
When("We try to PUT without proper role")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_norole").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 403")
|
||||
responsePut.code should equal(403)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(UserHasMissingRoles)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail with invalid JSON body", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We PUT with invalid JSON")
|
||||
val putValue = """{"invalid": "no value field"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_invalid_json").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 400")
|
||||
responsePut.code should equal(400)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidJsonFormat)
|
||||
}
|
||||
|
||||
scenario("PUT WebUiProp - fail with name exceeding 255 characters", VersionOfApi, ApiEndpoint2) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
When("We create a webui prop with name exceeding 255 chars")
|
||||
val longName = "webui_" + ("a" * 250) // 256 chars total
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / longName).PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 400")
|
||||
responsePut.code should equal(400)
|
||||
val error = responsePut.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
error.message should include("255 characters")
|
||||
}
|
||||
}
|
||||
|
||||
feature("Delete WebUiProp (DELETE) v6.0.0") {
|
||||
|
||||
scenario("DELETE WebUiProp - delete existing property successfully", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
|
||||
When("We create a webui prop")
|
||||
val putValue = """{"value": "to be deleted"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_delete").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
Then("We should get a 201")
|
||||
responsePut.code should equal(201)
|
||||
|
||||
When("We delete the webui prop")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_test_delete").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 204 No Content")
|
||||
responseDelete.code should equal(204)
|
||||
responseDelete.body.toString should equal("{}")
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - idempotent delete (delete twice)", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
|
||||
When("We create a webui prop")
|
||||
val putValue = """{"value": "to be deleted twice"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_test_delete_twice").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
responsePut.code should equal(201)
|
||||
|
||||
When("We delete the webui prop first time")
|
||||
val requestDelete1 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_delete_twice").DELETE <@(user1)
|
||||
val responseDelete1 = makeDeleteRequest(requestDelete1)
|
||||
Then("We should get a 204")
|
||||
responseDelete1.code should equal(204)
|
||||
|
||||
When("We delete the same webui prop again (idempotent)")
|
||||
val requestDelete2 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_delete_twice").DELETE <@(user1)
|
||||
val responseDelete2 = makeDeleteRequest(requestDelete2)
|
||||
Then("We should still get a 204")
|
||||
responseDelete2.code should equal(204)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - delete non-existent property (idempotent)", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
When("We delete a non-existent webui prop")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_never_existed").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 204 (idempotent)")
|
||||
responseDelete.code should equal(204)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - name converted to lowercase", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
|
||||
When("We create a webui prop with lowercase name")
|
||||
val putValue = """{"value": "test value"}"""
|
||||
val requestPut = (v6_0_0_Request / "management" / "webui_props" / "webui_delete_uppercase").PUT <@(user1)
|
||||
val responsePut = makePutRequest(requestPut, putValue)
|
||||
responsePut.code should equal(201)
|
||||
|
||||
When("We delete using UPPERCASE name")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "WEBUI_DELETE_UPPERCASE").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 204 (lowercase conversion works)")
|
||||
responseDelete.code should equal(204)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - fail without webui_ prefix", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
When("We try to delete with invalid name")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "invalid_name").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 400")
|
||||
responseDelete.code should equal(400)
|
||||
val error = responseDelete.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
error.message should include("must start with webui_")
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - fail with hyphen in name", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
When("We try to delete with hyphen in name")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_api-explorer").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 400")
|
||||
responseDelete.code should equal(400)
|
||||
val error = responseDelete.body.extract[ErrorMessage]
|
||||
error.message should include(InvalidWebUiProps)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - fail without authentication", VersionOfApi, ApiEndpoint3) {
|
||||
When("We try to DELETE without authentication")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_test_noauth").DELETE
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 401")
|
||||
responseDelete.code should equal(401)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - fail without CanDeleteWebUiProps role", VersionOfApi, ApiEndpoint3) {
|
||||
When("We try to DELETE without proper role")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_test_norole").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 403")
|
||||
responseDelete.code should equal(403)
|
||||
val error = responseDelete.body.extract[ErrorMessage]
|
||||
error.message should include(UserHasMissingRoles)
|
||||
}
|
||||
|
||||
scenario("DELETE WebUiProp - complete CRUD workflow", VersionOfApi, ApiEndpoint3) {
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanCreateWebUiProps.toString)
|
||||
Entitlement.entitlement.vend.addEntitlement("", resourceUser1.userId, CanDeleteWebUiProps.toString)
|
||||
|
||||
When("We create a webui prop")
|
||||
val putValue1 = """{"value": "initial value"}"""
|
||||
val requestPut1 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_crud").PUT <@(user1)
|
||||
val responsePut1 = makePutRequest(requestPut1, putValue1)
|
||||
Then("We should get a 201")
|
||||
responsePut1.code should equal(201)
|
||||
|
||||
When("We read the webui prop")
|
||||
val requestGet1 = (v6_0_0_Request / "webui-props" / "webui_test_crud").GET
|
||||
val responseGet1 = makeGetRequest(requestGet1)
|
||||
Then("We should get a 200 with correct value")
|
||||
responseGet1.code should equal(200)
|
||||
responseGet1.body.extract[WebUiPropsCommons].value should equal("initial value")
|
||||
|
||||
When("We update the webui prop")
|
||||
val putValue2 = """{"value": "updated value"}"""
|
||||
val requestPut2 = (v6_0_0_Request / "management" / "webui_props" / "webui_test_crud").PUT <@(user1)
|
||||
val responsePut2 = makePutRequest(requestPut2, putValue2)
|
||||
Then("We should get a 200")
|
||||
responsePut2.code should equal(200)
|
||||
|
||||
When("We read the updated webui prop")
|
||||
val requestGet2 = (v6_0_0_Request / "webui-props" / "webui_test_crud").GET
|
||||
val responseGet2 = makeGetRequest(requestGet2)
|
||||
Then("We should get the updated value")
|
||||
responseGet2.code should equal(200)
|
||||
responseGet2.body.extract[WebUiPropsCommons].value should equal("updated value")
|
||||
|
||||
When("We delete the webui prop")
|
||||
val requestDelete = (v6_0_0_Request / "management" / "webui_props" / "webui_test_crud").DELETE <@(user1)
|
||||
val responseDelete = makeDeleteRequest(requestDelete)
|
||||
Then("We should get a 204")
|
||||
responseDelete.code should equal(204)
|
||||
|
||||
When("We try to read the deleted webui prop")
|
||||
val requestGet3 = (v6_0_0_Request / "webui-props" / "webui_test_crud").GET
|
||||
val responseGet3 = makeGetRequest(requestGet3)
|
||||
Then("We should get a 400 (not found in database)")
|
||||
responseGet3.code should equal(400)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Loading…
Reference in New Issue
Block a user