Kuzzle anonymous user to access to a plugin? - plugins

Hi i tried to give anonymous user to access to a plugin but it still does not work what you think i am doing wrong?
kuzzle-core-plugin-boilerplate/NewController:Object
actions:Object
getamount:true
should anonymous get any other privilege to access the plugin?

By default, the anonymous user is not restricted and can call every API method (core methods and also plugin methods).
For example, if you have a plugin named iot in the manifest and you declare the following controller:
this.controllers = {
sensors: {
register: request => /* ... */
}
}
Then you can call this custom API action with the following WebSocket payload:
{
"controller": "iot/sensors",
"action": "register",
"body": /* request body */
}
If you want to call this API method with the Http protocol then you have to declare a route:
this.routes = [
{ verb: 'POST', url: '/sensors', controller: 'sensors', action: 'register' }
]
Then you can call it with Curl for example: curl -X POST http://localhost:7512/_plugin/iot/sensors

Related

CDK API Gateway default authorizer exclude OPTIONS method

I'm creating a LambdaRestApi in CDK and I want to have both CORS enabled and add an ANY proxy using the addProxy method.
I currently have the following CDK code:
const api = new LambdaRestApi(...); // This API has CORS enabled in defaultCorsPreflightOptions
const apiProxy = api.root.addProxy({
defaultMethodOptions: {
authorizationType: AuthorizationType.COGNITO,
authorizer: new CognitoUserPoolsAuthorizer(...),
}
});
The problem I'm running into is that while a proxy is created with the ANY method, it also sets the OPTIONS method to require authentication. I tried to add an OPTIONS method to the proxy using addMethod to override the authorizer but I get an error that there's already a construct with the same name. I'm also trying to avoid having to set the anyMethod field in the proxy to be false and adding my own methods. Is there a way in the API Gateway CDK to set the default authorizer to only work for any method except the OPTIONS method?
There is also a possibility to remove the auth explicitly on the OPTIONS method, here I also remove requirement for X-API-Key in the requests
const lambdaApi = new apigateway.LambdaRestApi(...) // This API has CORS enabled in defaultCorsPreflightOptions
lambdaApi.methods
.filter((method) => method.httpMethod === "OPTIONS")
.forEach((method) => {
const methodCfn = method.node.defaultChild as apigateway.CfnMethod;
methodCfn.authorizationType = apigateway.AuthorizationType.NONE;
methodCfn.authorizerId = undefined;
methodCfn.authorizationScopes = undefined;
methodCfn.apiKeyRequired = false;
});
I ran into the same issue when building a RestApi using the aws cdk. Here is a workaround where you can build the api piece by piece.
Declare the api construct without the defaultCorsPreflightOptions property, otherwise you will not be able to override Authorization on the OPTIONS method.
import * as apigateway from '#aws-cdk/aws-apigateway';
import * as lambda from '#aws-cdk/aws-lambda';
const restAPI = new apigateway.RestApi(this, "sample-api");
Add your resources and methods. In this case, I want to add an ANY method with a custom authorizer on the "data" resource. You can do this with any other supported authorization mechanism. The proxy handler is a lambda function created with NodeJs.
const dataProxyLambdaFunction = new lambda.Function(this, "data-handler", {
code: lambda.Code.fromBucket(S3CODEBUCKET, "latest/js_data.zip"),
handler: "index.handler",
runtime: lambda.Runtime.NODEJS_14_X
});
const dataProxy = restAPI.root.addResource("data")
.addResource("{proxy+}");
dataProxy.addMethod("ANY", new apigateway.LambdaIntegration(dataProxyLambdaFunction , {
allowTestInvoke: true,
}), { authorizationType: apigateway.AuthorizationType.CUSTOM, authorizer: customLambdaRequestAuthorizer });
Now, you can add an OPTIONS method to this proxy, without authorization. I used a standardCorsMockIntegration and optionsMethodResponse object to reuse with other methods in my api.
const ALLOWED_HEADERS = ['Content-Type', 'X-Amz-Date', 'X-Amz-Security-Token', 'Authorization', 'X-Api-Key', 'X-Requested-With', 'Accept', 'Access-Control-Allow-Methods', 'Access-Control-Allow-Origin', 'Access-Control-Allow-Headers'];
const standardCorsMockIntegration = new apigateway.MockIntegration({
integrationResponses: [{
statusCode: '200',
responseParameters: {
'method.response.header.Access-Control-Allow-Headers': `'${ALLOWED_HEADERS.join(",")}'`,
'method.response.header.Access-Control-Allow-Origin': "'*'",
'method.response.header.Access-Control-Allow-Credentials': "'false'",
'method.response.header.Access-Control-Allow-Methods': "'OPTIONS,GET,PUT,POST,DELETE'",
},
}],
passthroughBehavior: apigateway.PassthroughBehavior.NEVER,
requestTemplates: {
"application/json": "{\"statusCode\": 200}"
}
});
const optionsMethodResponse = {
statusCode: '200',
responseModels: {
'application/json': apigateway.Model.EMPTY_MODEL
},
responseParameters: {
'method.response.header.Access-Control-Allow-Headers': true,
'method.response.header.Access-Control-Allow-Methods': true,
'method.response.header.Access-Control-Allow-Credentials': true,
'method.response.header.Access-Control-Allow-Origin': true,
}
};
dataProxy.addMethod("OPTIONS", standardCorsMockIntegration, {
authorizationType: apigateway.AuthorizationType.NONE,
methodResponses: [
optionsMethodResponse
]
});
When you deploy the API, you can verify using the API Gateway console that your methods have been setup correctly. The proxy's ANY method has authorization enabled while the OPTIONS method does not.
Reference to the GitHub issue that helped: GitHub Issue 'apigateway: add explicit support for CORS'

Why is my PaymentMethod ID not detected when I run my AWS stripe application via Docker?

I am learning web development and I am currently working on creating a lambda test application for stripe. The paymentMethod id from the front-end is not being detected by my lambda function when I run it locally by calling sam local start-api. I am doing my development on VS Code.
I followed the instructions on this page to create and run my application. My directory structure looks like this:
hello_world/app.py has my Lambda function.
The code for invoking the lambda end-point in script.jslooks like this:
var stripe = Stripe('pk_test_DIGITS');
var elements = stripe.elements();
form.addEventListener('submit', function(event) {
// We don't want to let default form submission happen here,
// which would refresh the page.
event.preventDefault();
stripe.createPaymentMethod({
type: 'card',
card: cardElement,
billing_details: {
// Include any additional collected billing details.
name: 'Jenny Rosen',
},
}).then(stripePaymentMethodHandler);
});
function stripePaymentMethodHandler(result) {
if (result.error) {
// Show error in payment form
} else {
// Otherwise send paymentMethod.id to your server (see Step 4)
fetch('http://127.0.0.1:3000/payment', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
payment_method_id: result.paymentMethod.id,
})
}).then(function(result) {
// Handle server response (see Step 4)
result.json().then(function(json) {
handleServerResponse(json);
})
});
}
}
I ran the application on the browser by doing this:
When I click on Pay from my browser I can see the response in the logs on my dashboard:
The following code is for my lambda function app.py:
import json
import stripe
import requests
import logging
stripe.api_key= "sk_test_DIGITS"
def process_payment(event, context):
try:
print("START PRINTING")
print(event)
print("END PRINTING")
intent = stripe.PaymentIntent.create(
payment_method = 'event["body"]["payment_method_id"]',
amount = 1555,
currency = 'usd',
confirmation_method = 'automatic',
confirm = True,
payment_method_types=["card"]
)
return {
"statusCode": 200,
"body": json.dumps({
'clientSecret': intent['client_secret'],
# "location": ip.text.replace("\n", "")
}),
}
except Exception as e:
return {
"statusCode": 400,
"body": json.dumps({
"message": str(e),
# "location": ip.text.replace("\n", "")
}),
}
My template.yaml is as follows:
Globals:
Function:
Timeout: 30
Resources:
StripePaymentProcessor:
Type: AWS::Serverless::Function
Properties:
CodeUri: hello_world/
Handler: app.process_payment
Runtime: python3.6
Events:
Payment:
Type: Api
Properties:
Path: /payment
Method: post
Outputs:
HelloWorldApi:
Description: "API Gateway endpoint URL for Prod stage for Payment function"
Value: !Sub "https://${ServerlessRestApi}.execute-api.${AWS::Region}.amazonaws.com/Prod/payment/"
HelloWorldFunction:
Description: "Payment Lambda Function ARN"
Value: !GetAtt StripePaymentProcessor.Arn
HelloWorldFunctionIamRole:
Description: "Implicit IAM Role created for Payment function"
Value: !GetAtt StripePaymentProcessorRole.Arn
While keeping the browser window open, I ran the sam build command and it worked properly. After that I ran the sam local invoke command and it produced the following output:
I do not understand why event is empty. Should it not show the JSON data that got produced when I hit the pay button?
To do some trouble-shooting, I ran sam local start-api, invoked the POST method on Postman by pasting the JSON body from my Stripe logs:
What I did on Postman makes no sense to me and the snippet above raised another question for me. I do not understand why I see "message": "string indices must be integers" as a response on Postman.
EDIT:
After following wcw's suggestion I edited my fetch code to look like this:
I did not not see any written matter on the console by changing my code in this way.
I am keeping the browser open via the command prompt and I ran sam local start-api via the VS code console to keep http://127.0.0.1:3000/payment open. When I clicked on the pay button, I got the following response:
So the image above seems to indicate that the lambda function is not detecting the paymentmethod body.

How to make POST call using FOSRestBundle

I am trying to setup a RESTFUL web service using FOSRestBunble, but I have some problem making POST calls, here's my setup:
app/config/routing.yml
rest:
type: rest
resource: "routing_rest.yml"
prefix: /api
app/config/routing_rest.yml
Rest_User:
type: rest
resource: "#AppBundle/Resources/config/routing_rest.yml"
AppBundle/Resources/config/routing_rest.yml
rest_application:
type: rest
resource: "AppBundle:Rest"
name_prefix: api_
AppBundle/Controller/RestController.php
class RestController extends FOSRestController
{
public function testrestAction(Request $request)
{
$r = [
'is' => 'TEST'
];
return $r;
}
public function getArticleAction()
{
$r = [
'is' => 'GET'
];
return $r;
}
public function postArticleAction()
{
$r = [
'is' => 'POST'
];
return $r;
}
}
I also made PUT and DELETE test methods. so when I do some test call
GET /api/testrest
{
"is": "TEST"
}
GET /api/article
{
"is": "GET"
}
POST /api/article
No route found for "POST /api/article": Method Not Allowed (Allow: GET, HEAD) (405 Method Not Allowed)
PUT and DELETE are also fine. Am I missing some configuration?
second problem: if I make a API folder inside Controller folder, I change the namespace for RestController to "namespace AppBundle\Controller\API;" and I update "AppBundle/Resources/config/routing_rest.yml" to
resource: "AppBundle:API:Rest"
then I got this message:
Can't locate "AppBundle:API:Rest" controller in /var/www/ws/app/config/routing_rest.yml (which is being imported from "/var/www/ws/app/config/routing.yml").
any help appreciated
1-option, run app/console debug:router (or bin/console debug:router if v > 2.8), to list generated routes;
2-option, add RouteResource annotation to class (eg. article), rename postArticleAction to postAction and check POST /api/articles is responding or not;
3-option, add article url explicitly with #POST annotation, eg. /** #Post("article") */

Sails.js CORS for post method

I was able to use CORS for a specific controller using a GET request like the following:
'get /url': {
controller: 'somecontroller',
action: 'someaction',
cors: true
},
However if I try using POST like the following, I get "Access Denied" error:
'post /url': {
controller: 'somecontroller',
action: 'someaction',
cors: true
},
How do I setup cors for a post method?
in config/routes.js before declaring routes put :
'OPTIONS /*': function(req, res) {
res.send(200);
},
and in config/cors.js try to put :
module.exports.cors = {
allRoutes: true,
origin: '*',
credentials: true,
methods: 'GET, POST, PUT, DELETE, OPTIONS, HEAD',
headers: 'content-type, access-control-allow-origin, authorization'
};
With my limited research I found out that simply adding "cors: true" to the controller doesn't solve the problem. Sails is still expecting a csrf token for the post method. In the bootstrap.js file under config folder, I added the following code at the bottom to disable csrf token on the route by using the following:
sails.config.csrf.routesDisabled = '/url';
If you have better solutions, please post them here. Thanks!
Edit: You can also change this in the config/csrf.js file. Change module.exports.csrf = true; to:
module.exports.csrf = {
routesDisabled: '/url',
};
You might have to use it for your apis
module.exports.csrf = {
routesDisabled: '/api/*',
};

In Extjs5, erase() can't relate to destory api when the proxy type is rest

This is my viewController:
onRestDeleteClick: function(){
var ouType = Ext.create('MyApp.model.OuType',
{
id: 49,
ouTypeName: 'Lenlee',
entityName: 'Lenlee'
});
ouType.erase();
}
The model whose id is 49 exists in database.
This is the OuType model:
Ext.define('MyApp.model.OuType', {
extend: 'Ext.data.Model',
requires: [
'Ext.data.field.Field'
],
fields: [
{
name:'id'
},
{
name: 'ouTypeName'
},
{
name: 'entityName'
}
],
proxy:{
type: 'rest',
api: {
read: 'role/read',
update: 'role/update',
create: 'role/create',
destory: 'role/destory'
}
}
});
This is my server class:
#RequestMapping("/role")
#Controller("sysRoleContro")
public class SysRoleController {
…………
…………
#RequestMapping(value="/destory/{id}")
public void destoryOuType(HttpServletRequest request,
HttpServletResponse response, #PathVariable("id") Long id){
log.info("destory");
ouTypeRepository.delete(id);
log.info("end");
}
………
……
}
Now when i click the delete button, the request url is: http://localhost:7080/MyApp.model.OuType/49 404 Not Found.
The expected url is http://localhost:7080/CSQMS/role/destory/49
How can i delete the model?
Rest proxy is special in that that it does not CRUD operations to urls, as you set in api, but to HTTP verbs: GET, POST, PUT, DELETE, etc. So api config is most likely ignored. Configure the proxy this way:
proxy:{
type:'rest',
url:'/CSQMS/role'
}
If your server expects that CRUD operation verb is part of the URL you probably need a different proxy or you need to implement buildUrl method.
I want to say i'm so careless, i should write 'destroy' instead of 'destory'. MY GOD.