AWS SDK の各言語版がどのように生成されているのかちょっと見てみた go, JavaScript 編

2017.12.22

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

こんにちは。齋藤です。

今回は他の方が書かれていた記事に乗っかります。

この記事で書くのは 「golang と JavaScript の AWS SDKがどのように生成されているかについて」、です。

今回、この記事で紹介する 2つのSDK に関しては、両方とも SDKが記述されている言語で書かれていることが分かりました。 また、どちらのSDKもメタデータをjsonで表現して、そのデータを使ってコードの生成を使っているように見えます。

早速ですが、golang と JavaScript についてそれぞれ見ていきましょう。

golang の場合

golang では golangでの自動生成を行なっているようです。

S3のコードを見てみます。 先頭に次のような記述が書かれています。

// Code generated by private/model/cli/gen-api/main.go. DO NOT EDIT.

package s3

import (
	"fmt"
	"io"
	"time"

	"github.com/aws/aws-sdk-go/aws"
	"github.com/aws/aws-sdk-go/aws/awsutil"
	"github.com/aws/aws-sdk-go/aws/request"
	"github.com/aws/aws-sdk-go/private/protocol"
	"github.com/aws/aws-sdk-go/private/protocol/restxml"
)

この辺のapi.goを見ると "text/template"による生成をやっているようです。

// +build codegen

// Package api represents API abstractions for rendering service generated files.
package api

import (
	"bytes"
	"encoding/json"
	"fmt"
	"io/ioutil"
	"path"
	"path/filepath"
	"sort"
	"strings"
	"text/template"
	"unicode"
)

この辺の記述を見ると分かるように api.goのソースコード内に template の文字列がそのまま書かれていることが分かります。

// {{ .StructName }} provides the API operation methods for making requests to
// {{ .Metadata.ServiceFullName }}. See this package's package overview docs
// for details on the service.
//
// {{ .StructName }} methods are safe to use concurrently. It is not safe to
// modify mutate any of the struct's properties though.
type {{ .StructName }} struct {
	*client.Client
}

というわけで、テンプレートエンジンとしては text/template を使って、golang自身で生成されているようですね。

JavaScript の場合

今度はJavaScriptの場合です。こちらもJavaScriptによって記述されているようです。

client-creatorというファイルがあります。 それっぽい名前をしていますね。

このファイルにはgenerateClientFileSourceという関数が存在します。 この中では次のようなコードが書かれています。

  var code = '';
  code += 'require(\'../lib/node_loader\');\n';
  code += 'var AWS = require(\'../lib/core\');\n';
  code += 'var Service = AWS.Service;\n';
  code += 'var apiLoader = AWS.apiLoader;\n\n';
  code += 'apiLoader.services[\'' + serviceName +'\'] = {};\n';
  code += 'AWS.' + className + ' = Service.defineService(\'' + serviceName + '\', [\'' + [].concat(obsoleteVersions, versionNumbers).sort().join('\', \'') + '\']);\n';

ゴリゴリ文字列結合されている感じのようです。

また、d.tsなどのファイルもJavaScriptから生成されているように見えます

ところでこちらはgolang版とは違い、自動生成されているにも関わらず DO NOT EDIT といったコメントがないですね。

まとめ

他の方が書かれた記事では AWS SDK の生成方法は テンプレートエンジンを使ったものによる生成がされていました。

今回見た 2つのSDKは 標準ライブラリによるテンプレートエンジン と ゴリゴリ文字列結合で生成 と 他の言語とは少し違う形で書かれておりました。

今回の記事は他の方の記事に触発されて書きましたが ここまで大規模でしっかりとメンテナンスされているのは、非常に興味深いですね。

今回の記事はここまでです。

お腹が空きました。今日で仕事納めなので 美味しいものでも食べにいきましょう。

では、また来年の記事でお会いしましょう。