aws 合成金丝雀禁止错误 AWS Lambda 函数 URL

问题描述 投票:0回答:1

我尝试使用来自aws合成金丝雀的lambda url调用lambda函数,当我在邮递员中提供我的秘密和访问密钥时,它可以工作,但不能从aws合成金丝雀我遵循aws官方文档提供lambda:InvokeFunctionUrl政策,但仍然出现禁止错误

amazon-web-services aws-lambda
1个回答
0
投票

我发现下面是我的合成金丝雀 lambda,我正在其中创建 aws 签名来签署 http 请求。 任何有问题的人只需更改 accessKey、secretKey 和 URL

const crypto = require('crypto');
const synthetics = require('Synthetics');
const log = require('SyntheticsLogger');
const syntheticsConfiguration = synthetics.getConfiguration();

const apiCanaryBlueprint = async function () {
    syntheticsConfiguration.setConfig({
        restrictedHeaders: [],
        restrictedUrlParameters: []
    });

    // AWS credentials from environment variables
    const accessKeyId = "${accessKeyId}";
    const secretAccessKey = "${secretAccessKey}";
    const endpointUrl = "${endpoint_url}";

    // Helper function to create AWS Signature Version 4 headers
    function signRequest(requestOptions, region, service) {
        const endpoint = new URL('https://' + requestOptions.hostname + requestOptions.path);
        const method = requestOptions.method || 'GET';
        const now = new Date();
        const amzDate = now.toISOString().replace(/[:-]|\.\d{3}/g, '');
        const dateStamp = amzDate.slice(0, 8);

        // Canonical request
        const canonicalUri = endpoint.pathname;
        const canonicalQuerystring = '';
        const canonicalHeaders = 'host:' + endpoint.hostname + '\n' + 'x-amz-date:' + amzDate + '\n';
        const signedHeaders = 'host;x-amz-date';
        const payloadHash = crypto.createHash('sha256').update(requestOptions.body || '', 'utf8').digest('hex');
        const canonicalRequest = method + '\n' + canonicalUri + '\n' + canonicalQuerystring + '\n' + canonicalHeaders + '\n' + signedHeaders + '\n' + payloadHash;

        // String to sign
        const algorithm = 'AWS4-HMAC-SHA256';
        const credentialScope = dateStamp + '/' + region + '/' + service + '/aws4_request';
        const stringToSign = algorithm + '\n' + amzDate + '\n' + credentialScope + '\n' + crypto.createHash('sha256').update(canonicalRequest, 'utf8').digest('hex');

        // Calculate the signature
        const signingKey = getSignatureKey(secretAccessKey, dateStamp, region, service);
        const signature = crypto.createHmac('sha256', signingKey).update(stringToSign, 'utf8').digest('hex');

        // Add headers to request options
        requestOptions.headers['x-amz-date'] = amzDate;
        requestOptions.headers['Authorization'] = algorithm + ' Credential=' + accessKeyId + '/' + credentialScope + ', SignedHeaders=' + signedHeaders + ', Signature=' + signature;
    }

    // Helper function to derive the signing key
    function getSignatureKey(key, dateStamp, regionName, serviceName) {
        const kDate = crypto.createHmac('sha256', 'AWS4' + key).update(dateStamp).digest();
        const kRegion = crypto.createHmac('sha256', kDate).update(regionName).digest();
        const kService = crypto.createHmac('sha256', kRegion).update(serviceName).digest();
        const kSigning = crypto.createHmac('sha256', kService).update('aws4_request').digest();
        return kSigning;
    }

    const validateSuccessful = async function (res) {
        return new Promise((resolve, reject) => {
            if (res.statusCode < 200 || res.statusCode > 299) {
                throw new Error(res.statusCode + ' ' + res.statusMessage);
            }

            let responseBody = '';
            res.on('data', (d) => {
                responseBody += d;
            });

            res.on('end', () => {
                resolve();
            });
        });
    }

    function extractRequestOptions(endpointUrl) {
        // Parse the URL using the URL constructor
        const parsedUrl = new URL(endpointUrl);

        // Create an object similar to requestOptionsStep1
        const requestOptions = {
            hostname: parsedUrl.hostname,
            method: "POST",
            path: parsedUrl.pathname,
            port: parsedUrl.port || '443',
            protocol: parsedUrl.protocol,
            body: "",
            headers: {}
        };

        return requestOptions;
    }

    // Set request option for Verify
    let requestOptionsStep1 = extractRequestOptions(endpointUrl);

    // Sign the request manually
    signRequest(requestOptionsStep1, 'ca-central-1', 'lambda');

    // Add the User-Agent header
    requestOptionsStep1['headers']['User-Agent'] = [synthetics.getCanaryUserAgentString(), requestOptionsStep1['headers']['User-Agent']].join(' ');

    let stepConfig1 = {
        includeRequestHeaders: false,
        includeResponseHeaders: false,
        includeRequestBody: false,
        includeResponseBody: false,
        continueOnHttpStepFailure: true
    };

    await synthetics.ex
© www.soinside.com 2019 - 2024. All rights reserved.