Как использовать select_object_content через rusoto / rust?

Следующий код пытается выбрать некоторые данные из файла, хранящегося на S3:

  let client = S3Client::new(Region::default());
  let source = ... object providing bucket and key ...;

  let r = SelectObjectContentRequest {
      bucket: source.bucket,
      key: source.key,
      expression: "select id from S3Object[*].id".to_string(),
      expression_type: "SQL".to_string(),
      input_serialization: InputSerialization {
          json: Some(JSONInput { type_: Some("LINES".to_string()) }),
          ..Default::default()
      },
      output_serialization: OutputSerialization {
          json: Some(JSONOutput { record_delimiter: Some("\n".to_string()) }),
          ..Default::default()
      },
      ..Default::default()
  };

Это вызывает следующую ошибку:

Указанный метод не разрешен для этого ресурса.

Примером является порт 1:1 рабочего примера Python/boto3, поэтому я вполне уверен, что он должен работать. Я обнаружил эту проблему, которой уже несколько месяцев, и статус которой мне не ясен. Как мне заставить это работать с Rust?

1 ответ

К сожалению s3 select все еще не работает на последней rusoto_s3-0.40.0, У проблемы, которую вы связали, есть все ответы. Проблемы двоякие.

Во-первых, прямо сейчас запрос выбора s3 rusoto отсылает имеет поддельную строку запроса. Так должно быть /ObjectName?select&select-type=2, но rusoto кодирует это быть /bjectName?select%26select-type=2, Это ошибка, которую вы видели.

Чтобы проверить, запустите ваш проект так:

$ RUST_LOG=rusoto,hyper=debug cargo run

Вы увидите журналы от rusoto а также hyper, Конечно же, он выдает неверный URI. Можно даже покопаться в ответственном коде:

let mut params = Params::new();
params.put("select&select-type", "2");
request.set_params(params);

Это должно быть:

let mut params = Params::new();
params.put("select-type", "2");
params.put("select", "");
request.set_params(params);

Хотя исправление кажется тривиальным, помните, что это клейкий код, сгенерированный из сервисных манифестов AWS Botocore, а не закодированный вручную. Чтобы исправить это не так просто.

Во-вторых, большая проблема. Ответ AWS s3 select использует настроенный двоичный формат. rusoto просто еще нет десериализатора для этого.

Другие вопросы по тегам