Аутентифицированная конечная точка AWS API Gateway Загрузка файла POST Запрос Подпись Несоответствие - PullRequest
0 голосов
/ 14 ноября 2018

В настоящее время работает над клиентским клиентским приложением Angular 6, которое использует конечную точку шлюза API AWS, для которой включена авторизация IAM, чтобы загрузить файл со связанными метаданными, чтобы в конечном итоге он находился в корзине S3.

Приложение javascript использует объект FormData для инкапсуляции объекта файла и метаданных и выполняет HTTP-запрос POST через Angular HttpClient API и aws-sign-web для подписи заголовка запроса SigV4. В настоящее время у меня возникает проблема при выполнении запроса POST к AWS API Gateway, который отмечает, что подписанный запрос не совпадает, и получаю следующее сообщение об ошибке от AWS; «Рассчитанная нами подпись запроса не соответствует предоставленной вами подписи. Проверьте свой секретный ключ доступа AWS и метод подписи».

Примечание: POST-запрос на загрузку файла работает нормально, если авторизация IAM не включена.

Вот фрагмент кода запроса Angular со знаком:

onSubmit() {

    // clear response messages to hide as necessary
    this.response_message = '';
    this._err.message = '';
    const dataUrl: string = this.baseUrl + '/api/UploadDB/Post';

    // disable submit button
    this.disableSubmit = true;
    this.sort_id = this.getSortID();
    const currentFile: string = this.buildFileName();

    // append file and parameters to form
    const uf = this.upload_file.nativeElement;
    if (uf.files && uf.files[0]) {

        const file = uf.files[0];

        // check file extension to verify .htm/.html
        if (this.checkFileType(file.name)) {

            const formData: FormData = new FormData();
            formData.append('file', file, currentFile);
            formData.append('sortid', this.sort_id);

            // set HTTP headers from aws-sign-web utility
            const headers = this.AWSService.CreateAWSSignedPostRequest(dataUrl, 'POST', formData, this._AuthCredentials.AccessKeyId,
                                                this._AuthCredentials.SecretAccessKey, this._AuthCredentials.SessionToken);

            // set request headers
            const req_options = {
                headers: headers

            };

            this.http.post(dataUrl, formData, req_options).subscribe(
                response => {
                    this.response_message = 'The following file ' + file.name + ' was published successfully.';

                    // clear form
                    this.uploadForm.reset();
                    this.upload_file.nativeElement.value = '';

                    // reset the file browser select label
                    this.upload_file_label = this.upload_file_default_label_msg;

                },
                error => {

                    this._err = <Error>error.json();

                    // re-enable submit after error response
                    this.disableSubmit = false;
                }
            );

        } else {
            // invalid file type return error message
            // tslint:disable-next-line:max-line-length
            this._err.message = 'errmessage;
            this.disableSubmit = false;
        }
    } else {
        // there was a problem with the selected file prior to upload
        this._err.message = 'errmessage';
        this.disableSubmit = false;
}

public CreateAWSSignedPostRequest(dataURL: string, method: string, formData: 
                               any, accessKeyID: string,
    secretAccessKey: string, sessionToken: string): HttpHeaders {

    // declare variables
    let headers: HttpHeaders = new HttpHeaders();


    // set aws config parameter
    const config: Config = {
        region: environment.region,
        service: 'execute-api',
        accessKeyId: accessKeyID,
        secretAccessKey: secretAccessKey,
        sessionToken: sessionToken
    };

    // create aws-sign-web object
    const signer = new AwsSigner(config);

    // declare aws-sign-web request object
    const request = {
        method: method,
        url: dataURL,
        body: formData
    };

    // sign aws request
    const signed = signer.sign(request);

    console.log(signed);

    // loop through signed request objects and map to Headers list object
    for (const attribute in signed) {
        if (signed[attribute]) {
            headers = headers.append(attribute, signed[attribute]);
        }
    }

    return headers;

}

Любая помощь приветствуется в устранении этого несоответствия подписанного запроса для отправки HTTP-запросов POST в API Gateway с файлом multipart / form-data.

...