有没有办法使用 Google 图表 API 的 POST 方法通过 Google Apps 脚本获取 QR 码图像?

Is there a way to get a QR code image with Google Apps Script using the POST method of the Google Charts API?

我正在使用 Google 脚本生成活动门票,门票包含一个 QR 码,该二维码将转到预先填写的 Google 表格 link。由于它是预填充的,字符串很长,用于创建二维码的 Google 图表 API 不会接受使用 GET 请求的文本字符串,但我找不到任何有关如何将 POST 请求编码为 Apps 脚本的文档。我如何在 Apps 脚本中生成一个 POST 请求,该请求将 return 我可以插入到文档中的二维码图像?

我已经尝试了 GET 请求,它在将 URL 编码为二维码之前截断了它。这让我进入了 Google 表单,但不是 link 生成的预填充版本(实际上 Google 的部分非常聪明,让它在一个地方截断字符串仍然提供可用的 URL,但那是另一天...)

我也尝试过 HtmlService 使用 POST 方法和图表 API 以 HTML 形式呈现 QR 码,该 HTML 表单在加载时自动提交 HTML。如果我使用 showSidebar(),这将在新选项卡中打开图像,但我还不知道如何 return 该图像以便将其插入到文档中。

我也尝试过使用 HTML 创建一个 blob,然后将 blob 保存为 PNG,但是根据我所做的研究,.getAs() 方法在以下情况下不会渲染图像转换 HTML.

renderQR 函数:

function renderQR(inputUrl) {
  var html = HtmlService.createTemplateFromFile('QREncode.html');
  html.url = inputUrl;  
  var rendered = html.evaluate().setSandboxMode(HtmlService.SandboxMode.IFRAME)
    .setHeight(300)
    .setWidth(300);
 return rendered;   
}

QREncode.html 文件:

<!DOCTYPE html>
<html>
  <head>
    <base target="_top">
    <script type='application/javascript'>
    // Send the POST when the page is loaded,
    // which will replace this whole page with the retrieved chart.
    function loadGraph() {
      var frm = document.getElementById('post_form');
      if (frm) {
       frm.submit();
      }
    }
    </script>
  </head>
  <body onload="loadGraph()">
    <form action='https://chart.googleapis.com/chart' method='POST' id='post_form'>
       <input type='hidden' name='cht' value='qr' />
      <input type='hidden' name='chl' value='<?= url ?>' />
      <input type='hidden' name='chs' value='300x300' />
      <input type='submit'/>
    </form>    
  </body>
</html>

当我将 renderQR() 函数中的 return 视为图像时,Apps 脚本给出一个错误,指出它是 "Invalid image data",这是有道理的——但我该如何转换它变成图像,或者有更好或更简单的方法吗?

您需要在 Apps 脚本中获取二维码,而不是在浏览器中:

  var imageData = UrlFetchApp.fetch('https://chart.googleapis.com/chart', {
    'method' : 'post',
    'payload' : {
      'cht': 'qr',
      'chl': 'https://google.com',
      'chs': '300x300'
  }}).getContent();