冥冥乃志

ソフトウェア開発会社でチームマネージャをしているエンジニアの雑記。アウトプットは少なめです。

follow us in feedly

Serverless Frameworkを使ってみる

先日、社内システムの一部を再検討するときに、API Gateway + LambdaでServerlessマイクロサービスを選択肢に入れておこうという話をしました。で、言い出しっぺでほっとくのもあれなので、ちょっと自前で検証しておこうというのがこのエントリです。Lambda触ってみたかったですし。

本当だったら開発フローや近隣プロジェクトの開発者へのドキュメントやライブラリ公開まで含めた継続的デプロイまで整備してからリファレンスアーキテクチャ的な形のものを発信したかったんですけど、思ったより検証範囲が大きくなりすぎるので、Serverless frameworkを使ってデプロイしてみたところでエントリ的には一旦区切ります。もう何番煎じかわからないので、細かい設定などは書かずに、やりたいことと参考のリファレンスを整理していこうと思います。

その後の経過については別エントリであげる予定。

先に現状のリポジトリをご査収ください。

github.com

Serverless framework is 何?

serverless.com

Serverlessアーキテクチャを作るためのフレームワークとツール類をまとめたものです。AWSだけを対象にしたものではなく、Azureなどの各種クラウド環境に対応しています。LambdaのキックイベントはAPI Gatewayに限らず、S3の更新やCloudWatchあたりを設定することができます。今回私はPythonを使ってプロジェクトを作成しました。AWS関連のエントリではいつも大変お世話になってるクラメソさんのブログを読めば一通り使うことができます。

dev.classmethod.jp

デプロイ時の定義は serverless.yml という設定ファイルに記述され、記述に基づいたアプリケーションの構成をCloudFormationで作って後はよしなにしてくれます。Elastic Beanstalkと同じく、後からCloudFormationとかの構成の設定をみて勉強するという使い方もありかもしれません。

ちなみに、デフォルトだとイベント設定されていないので、そのままデプロイしてもAPI GatewayAPIは作成されません。また、デフォルトのリージョンはus-east-1です。東京リージョンにデプロイするときは serverless.yml にリージョンをちゃんと指定しておきましょう。

ちなみに、細かい話ですがデプロイしたLambdaファンクションの反映にはコンソールで10〜20秒くらいラグがありました。そんなもんなんですかね?テンプレートで出力されたプロジェクトをテスト的にデプロイしてキックするだけならLambdaの無料枠を超えることもないでしょうから、CloudFormation設定を確保するS3の利用料くらいですみます。

ドキュメント

充実しているのでここから探しましょう。

serverless.com

まずはGuideから読んでいけばいいと思います。最初に動かすまでは、Resource,Variables,Packaging,IAMあたりは必要に応じて読むくらいの心持ちで、大丈夫かと。

ただし、Workflowは読んで置くべきです。

serverless.com

開発時の変更ケースに沿ったデプロイの流れやstageやサービスレベルでのアカウント管理についての注意事項、Serverless Architectureの設計上の勘所あたりが書いてあってとても有用です。

Pythonに関する自分用リンク

まだなんとなくな理解の部分

  • stageって何?
  • CloudFormationちゃんと使ったことない
  • version のピン打ちができるけど、CIとかかけるんだったらやっといた方がいいかも
  • Lambdaに置けるエラー処理は結局どうやるのが良さげなのか 関数エラー (Python) - AWS Lambda
  • Lambdaファンクションの粒度 Step Functions使ったService層的なものの導入は必要になりそう

シンプルなレスポンスを返すマイクロサービスを作る

で、ここからが本題。実際に開発の場に持ち込むためには以下が足りないんですよ。

  • ローカル実行時のDynamoDBの取り扱い
  • テスト

どちらもない状態でチーム開発するのはしんどいですよね。というわけでこの辺りを整備してみます。

ローカル実行用にDynamoDBを使いたい

AWS上に作られているDynamoDBのテーブルにアクセスするのは簡単です。公式にもサンプルがあって、その通りに書けばとりあえずはデータのCRUDは試すことができます。

github.com

スキーマレスだからserverless.ymlにIDしか定義してなくてデータ突っ込んでるの強引だなあ、とか諸々思うところはあるのですが、それは今議論するところではないのでそっとしておきます。

で、CloudFormationがよしなにテーブル作ってくれたりするのはいいのですが、そのままでは一度でもデプロイしてしまうとローカル実行でもこのDynamoDBテーブルを使うようです。チームで使ったりする場合はちょっと不便。開発者の個別の実行は、AWSが用意しているDynamoDB ローカルを使ってあげるようにしたいですね。

docs.aws.amazon.com

で、見つけたのがこのプラグインです。

www.npmjs.com

で、私のソースは以下のQiita記事を参考に書いているので、 event[isOffline] を参照してデータソースを切り分けているのですが、

qiita.com

これは別のserverless-offline使う前提の名残です。なぜか私の環境ではpython3.6がunsupportedと出てるのでちょっと保留中です。ぶっちゃけserverless-offline自体はいらないんじゃないか、とも考え中。

Lambdaファンクションにテストを書きたい

初めはdoctestを使って書こうかと思ってたんですが、Lambdaファンクションのハンドラーになる関数だと、DynamoDBとかリソース使い出すとserverless.ymlのコンテキスト渡しづらくなってしんどいんですね。ファンクションの中で適切に分割されたpythonの関数であれば、doctestで十分にかけると思いますが。

というわけで、ハンドラーレベルのテストはServerless Frameworkのローカル実行機能を前提にbats使ってみることにしました。E2Eテストとユニットテストの2段階というイメージです。

qiita.com

リポジトリにもbotsを使ったテストを書いてます。が、一応、テストが書けたけど、シェルスクリプト力の不足でアサーションが非常に弱い状態。誰かまさかり投げて。。。

一旦のまとめ

というわけで、Serverless Frameworkを使ってチームでマイクロサービスを開発する上での方向性とか基盤の整理みたいなものの試行錯誤をしてみました。その一応の成果が先のリポジトリであります。いくつかいけてないところはありますが、そこはこれから洗練させる余地はあると思いますので、まずはこの辺で開発者視点は区切っておこうというのが今回のエントリの主旨です。

で、次はサービスのマネージャ視点になります。サービスは作って終わりではなく、他のサービスやアプリケーションの開発者に提供しなければならないリソースを整備することが必要になりますね、APIドキュメントとかライブラリとか。これらをデプロイに応じて自動で整備をする、というところをやっていきたいと思います。

Swaggerのファイル仕様が不満だったのでRAMLを触って比較してみる

前回、こういうの書きました。

mao-instantlife.hatenablog.com

で、最後に触れたSwaggerの定義ファイルへの不満点。これに悶々としていたところ、隣の席の人にRAMLというのを教えてもらったので比較がてら使ってみました。

RAML is 何?

Welcome | RAML

系統としてはSwaggerと同じく、yaml形式の仕様ファイルから公開向けドキュメントやライブラリ、サーバスタブなどを作るための定義仕様です。仕様のみの提供で、開発環境やコード生成ツールなどはサードパーティやコミュニティで開発されています。

例えばライブラリ生成なんかはこれ。

scraml.io

API Gatewayにデプロイしたいなーというときは、AWSが公式に出しているAPIGateway Importerを使いましょう。

github.com

開発環境

デファクトになりそうなのが、API WorkbenchとAPI Designerでした。以下、両者の概要を載せておきます。私はAPI Workbenchを使っています。

API Workbench

Atomプラグインとして提供されていますが、β版です。

API Workbench

一応0.8にも1.0にも対応を謳っていて、Swaggerの公式エディタやAPI Designerと違ってローカルのgitとも連携しやすいのが楽です。

Getting Started

Getting Startedで一通りRAMLの仕様を通り抜けられるところは好感高いです。ただし、まだβ版なので結構バギー。Getting Startedの通りにやろうとするとエラーになる(主にツールの操作で、ramlファイルの編集をすればいいので回避策はある)レベルの完成度。不安定ではありますが、提供されている機能的にも充実しているので使いながら待っていても十分なレベル。

API Designer

Swaggerのエディタと同じくWebベースのデザイナ、エディタです。保存はブラウザのLocal Databaseになります。RAMLはファイルの分割、インクルードができるので作ったらzipでダウンロードしてソース管理に、というワークフローになってちょっと辛いです。また、公式のdockerイメージもないので、その辺は改善して欲しいところ。

github.com

Swaggerと比較して嬉しいところ

で、数時間ほどAPI WorkbenchのGetting Startedを通しでやってみながら確認していたわけですが、Swaggerよりも嬉しいファイル仕様がいくつかありました。個人的にはこれがあるだけですごく嬉しい。どれも定義ファイルの記述を短く、シンプルにしてくれるものだと感じました。

リソースタイプ

リソース(URL)ごとにメソッドのパターンをまとめられる仕様です。inputとoutputは型パラメータのように抽象化して指定することが可能なので、再利用できます。だいたいAPIの構成ってリソースの種類ごとに似通う(in/outの型以外)よね、という発想はちゃんと仕様にしておいてくれて嬉しい限り。

resourceTypes:
  Collection:
    get:
      reponses:
        200:
          body:
            applicaton/json:
              type: <<item>>[]
    post:
      body:
        application/json:
          type: <<item>>

上記は GET でリソースのリストを返し、POST で新規作成する、 item を型パラメータとして持つリソースのパターンを示しています。これをあるリソースに適用するときはこんな感じです。

/newResource # これがURLになる箇所
  type: { Collection: {item: newResourceType} } # itemに実際の型定義を指定

トレイト

トレイトはリソース単位ではなくHTTPメソッドの振る舞い(パラメータのとり方とレスポンスの返し方、型)を抽象化することができる機能です。例えば、特定の項目に対するフィルタリングの振る舞いを複数のリソースの同じメソッドで実行する場合、以下のようなトレイトを用意します。

traits:
  FilterableByColumnKeyword:
    queryParameter:
      include:
        type: string
      exclude:
        type: string

これで、特定のキーワードが含まれる場合と含まれない場合のメソッドの振る舞いを定義しました。キーワードはクエリパラメータで指定する形式です。これをあるリソースのGETメソッドに定義する場合は以下です。

/newResource:
  get:
    is: [FilterableByColumnKeyword]

サブタイプ

型定義をシンプルにするためにサブタイプの定義仕様もあります。

例えば、Supertypeという基本的な型があって、その派生型で一部属性を共有するSubtypeがあるというケース。

type:
  Supertype:
    properties:
      id: string
      name: string
  Subtype:
    type: Supertype
    properties:
      company: string

のような定義で、Supertypeの定義に追加するような派生型が作れます。型のテンプレート的な用途で使うよりは、ちゃんとモデリングして派生の関係を作ってから定義した方がいいと思います。

uses定義

in/outの型やリソースタイプ、トレイトなどを別ファイルに切り出して定義して、それを読み込む機能です。Swaggerの言語仕様にこれが見つからなくてファイルがだだ長くなって「え〜」てな感じだったので、私にとってはこれだけでもRAML圧勝です。

uses:
  namespace: other_library.raml

のような形式で記述します。

結局やりたいことって

これから先、デプロイをサービス単位にAPI Gateway + LambdaみたいなServerlessにしていくのはデファクトになっていくのかなあ、と思っているのですが、開発者で共有するドキュメントは欲しいです。それに、サービスだけではなく、アプリケーションとして取りまとめるためにはライブラリも必要です。そのために境界はRAMLやSwaggerのようにそれらの生成を前提とした仕様定義を行って、サービスの実装はそれを元にServerless frameworkで行う、みたいな役割分担になってくるのかなあ、と思います。Serverless SPAみたいな構成だとそもそもServerless frameworkだけでいいじゃん、的な結論になると思いますが。

次は、Serverless frameworkを少し触ってからRAMLと繋いでみようかと。

ところで、サービスごとに分割して複数サービスを束ねてアプリケーション作るようなアーキテクチャにすると、トランザクションとか大変そうなんですが、みなさんどうしてるんでしょうね。後、DDDでいうサービス層の一部がフロントエンドでの実装に変わってしまうのではないかとも思ってて、この辺もみなさんどうしてるのか気になりますね。

Swaggerを使ってライブラリ非公開のAPIにライブラリを作って見た

仕事で少し検証をしてみたくなったAPIサービスが見つかりました。

codenberg.io

オンデマンドに印刷・発送をするためのAPIサービスなんですが、対応予定言語にJavaがない!REST APIだからどうとでもなるとは言え、フレームワーク的な部分のコードをゴリゴリと書きたくないですよね。本末転倒な楽しさに目覚めてしまう可能性もありますし(そっちかよ)。

というわけで、API仕様も公開されていますし、Swaggerの練習がてら自力でライブラリ生成をして使ってみました。

Swagger is 何?

swagger.io

Open API Specificationの開発者ツールフレームワークで、APIのデザイン、ドキュメンテーション、開発を支援する仕様とツール群を提供しています。Open API SpecificationとはアプリケーションにRESTful APIを作るための書式です。

ツール類は以下の3つで構成されています。

  • Swagger Editor -> まあその名の通り、オンラインエディタ(Local Datastoreに保存)かnodeかdockerを選べます
  • Swagger Codegen -> Open API Specificationから各種環境用のサーバスタブやライブラリを生成するためのツール
  • Swagger UI -> Open API Specificationからインタラクティブな機能を持った開発者向けドキュメントを生成するツールとその開発ドキュメントそのもの

今回サーバスタブは作っていません。

Open API Specification

細かい仕様はここを読みましょう。

Swagger Specification

定義はymlでもjsonでも書けます。エンドポイントや認証フロー、APIのIn/Outの各種データモデルを定義することができます。

Swaggerに感じる可能性

個人的には、このAPI SpecificationをAPI Gatewayに流してエンドポイントはそっちで管理、実装レイヤはAWS Lambdaという構成にできる方がいいのではないかと思っています。フロントエンドとサービスを切り離して、コンテキストでわけられた各種サービスのエンドポイントをつなぎ合わせて構成に、というとなんかMicroserviceっぽいですね。この構成にする上で、開発者に公開するドキュメントやライブラリは必須なわけですが、設計レベルからのアプローチで設計ドキュメントと実装の一致を測りやすくなっているのは良い感触です。

コンテキストの境界づけをAPIを提供する単位で行うことができ、別のコンテキストの裏口的なアクセスをなるべくブロックすることができます。そういう意味でDDDの各種実装パターンにおける実際のアーキテクチャのリファレンスが少し変わるのではないかと(パターン自体はあまり変わらないのではないかと思っている)。

というわけで使ってみた

swagger.yaml自体は仕様に基づいて書いただけなので、リポジトリをご査収ください。

github.com

で、検証している時にいくつか課題があったのでその内容をメモっておきます。

Swagger UIからAPIにアクセスできない

実際に仕様を書いてSwagger UIからアクセスしてみようとすると、こんなエラーが出ました。

Fetch API cannot load https://api.codenberg.io/v1/auth/token. Response to preflight request doesn't pass access control check: No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://editor.swagger.io' is therefore not allowed access. The response had HTTP status code 404. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.

Swagger UIからのアクセスは当然Originではないので、許可されていませんよ、ということ。オンラインエディタで最初に確認しましたが、dockerのコンテナ立ててlocalhostでエディタ立ててもVS Codeの拡張機能使っても同様でした。コンテナはまあ想像していましたが、VS Codeの拡張機能もnode使っているんでしょうね。ちなみに、認証に限らずAPI全般で同じ状態でした。

今回のケースはサーバサイドの問題です。どこまで許可するか、とかセキュリティの問題はありそうですが、少なくとも開発、テスト時に必要なレベルは許可されていないとツール類からアクセスできないのは非常に不便ですね。プルリクエスト投げた時にコメントで追加しています。

生成されるライブラリの認証フロー実装

Javaのライブラリを出力して、検証してみました。で、サンプルとして一緒に出力されるコードが以下のような感じなんですよね。

package sample;


import io.swagger.client.*;
import io.swagger.client.auth.*;
import io.swagger.client.model.*;
import io.swagger.client.api.FormatsApi;


/**
 * Created by mao on 2017/06/26.
 */
public class Application {


    public static void main(String[] args) {
        ApiClient defaultClient = Configuration.getDefaultApiClient();


        // Configure OAuth2 access token for authorization: codenberg_auth
        OAuth codenberg_auth = (OAuth) defaultClient.getAuthentication("codenberg_auth");
        codenberg_auth.setAccessToken("Access Token");


        FormatsApi apiInstance = new FormatsApi();
        try {
            InlineResponse2001 result = apiInstance.getFormats(new Body3());
            System.out.println(result);
        } catch (ApiException e) {
            System.err.println("Exception when calling FormatsApi#getFormatById");
            e.printStackTrace();
        }
    }
}

出力されるライブラリはOAuthの認証フローは実装されず、AccessTokenをセットする前提になっている。認証フローは別のライブラリなどで考慮する出力仕様のようです。他の言語のライブラリ出力ではどうなるかまでは検証していませんが、まあこの辺は知っていればいいだけの話かと。

あと、若干クラス名のつけ方が自動生成っぽいというかアレですね。この辺はもしかしたら定義の仕方次第で回避方法はあるのかも。

ちなみに、ライブラリからのアクセスはうまくいきました。いちいち出力して検証するわけには行かないので、クロスドメインの問題自体はサーバサイドで対応した方がいいですが、回避方法というか検証方法自体は残されている、ということで。

まとめ(というかお願いプリーズ)

自力でライブラリを生成して試せる、というのは非常にありがたいですね。API開発者は各言語用のライブラリを提供する必要はないので、swagger.yamlだけでも公開しておいてくれると非常に助かります。はいはいAPIね、Javaがねーじゃんそっ閉じってことをしなくて済むようになるので。

ちなみに私はSwaggerファイルの仕様というか、長くなりがちなファイル構成に不満がありまくりんぐでしたので、RAMLに乗り換えてみようかと思っております。

「二人で生きていく」という選択

これは、

www.adventar.org

の24日目のエントリのつもりでした。ちょうどこの時期に少し仕事が忙しくなり、バタバタしてたらそのままスルーしてしまって今に至る、と。長々と寝かせとくのもあれなので、成仏させてあげようと思います。

11/22で結婚してから丸14年、15年目の夫婦になりました。

故あって「二人だけ」

過去エントリ、

mao-instantlife.hatenablog.com

でも触れたことがあるのですが、私たちは「子供を作らないことを選択してから結婚した」夫婦です。その理由については同じく触れるつもりはありませんが、結婚に当たって非常に大きな選択をしたことになります。家族の形がどうあれ、この人と一緒に暮らしていきたかった、と思えた人と出会えたことがまず幸せですね。

二人で生きていく生活で楽な点

  • 共働きでなくてもなんとか生活できる
  • 家や車や保険がコンパクトでも良い
  • お互いの時間の持ち方について合意するのが簡単

生活費の面については、二人で生きていくことを選択した理由にもなっていますが、妻が急に働きに出たりなどがしづらいので、収入については私の一馬力を基本に考えないといけません。その点で家計がコンパクトになっていくのは良いことでした。家も保険も基本的に「後の世代に残す」ことを考えなくていいわけですから。

生活のあり方をコンパクトにしよう、と意識するようにはなりました。

二人で生きていく生活で不便な点

  • 初対面の人への説明が面倒
  • 交友関係が限定される

最近は、家族の形に関する有形無形の期待感みたいなものはなくなってきた(周りが慣れた?)ので、子供がいないと言っても特に怪訝な目を向けられることもなくなりました。それでも初対面であれば子供のことを聞かれることはあります。質問として無難ですからね、多分天気の次くらいに。「いないんですよ」で察してくれればいいですが、ごく稀に突っ込んだことを聞いてくる人もいるわけですね。この対応は若干疲労感激しいです。あ、でも、他のご家庭のお子さんのことを聞くのが嫌いなわけではないのでそこはご遠慮なく(少なくとも私は)。

交友関係については、場へのアクセスが限定される、というのが正確なところですね。年取ってくると趣味の場も減ってきますし。幸いにして我が家はご近所さんがかなり気さくな方なので、付かず離れずではありますが、全く交友がなくなってしまうということはないです。新しい人と出会うきっかけは着実に減ると思います。

幸いにして、私の方はコミュニティやCoderDojoなどで同世代や家族・ご近所のコンテキストに限らない交友関係を築けていますが、それもできる時とできない時があります。家庭や本業が優先されてしまいますので。

我が家特有の心配事

今年は妻の通院も多くなっていたり、もともと体が強くないのでその点で心配事が多くなったり、と仕事で「家を開ける」ことへの不便さを感じることが多くなってきました。どうしてもリモートワークの利点というのは考えてしまいますね。このご時世でのお仕事、場所を選ばずにできることは多いんだから、世間的にももっとリモートワークが当たり前になってくるといいなあ、とは思います。

飽きない?

全然。妻は楽しい人ですし、いつまで経っても可愛さを失わないですし、月一回のデートも楽しいです。この人だったら飽きないな、と思ったからこそ、二人で生きていく相手としてお互い選んだつもりです。

二人で始まって二人で終わる

ただ、いつかはこの生活も終わります。二人の中でそれはどちらかが死ぬ時だと思っています。

なるべく長く一緒にいて、なるべく同時にが理想だけど、なかなかそうも行かないからなるべく近づくように体を準備していこうとはしています。最近体づくりにこだわってきてるのもそういうこと。長生きにこだわっているわけではありませんが、なるべく病気をせずに、二人で過ごす時間を長くしようね、ということです。後に一人で残る時間が長いほど辛いので、今から「どう終わるのが理想的か」みたいなことは考えるようになっています。以前、「旅のことば」に触れたこともあるんですが、このような準備を少しずつでも進められるといいな、と。

mao-instantlife.hatenablog.com

その時に対してできるアクションを今から取ろうと決意した次第であります。これについては固まってきたらおいおい話できるといいなあ、とか。いつになるかとか言いませんがね。

ともあれ、家族の形とあゆみというのは家族の数だけある、ということです。みんなで幸せになろうぜ。

「正解するカド」を希望的妄想で解釈してみる(したいという9話、10話の感想)

9話ラストと10話での超展開、それら視聴後における阿鼻叫喚の感想の嵐と、今まで丁寧に「ちゃんとしたSF」を積み上げてきた感の本作への失望をあらわにする人が増えています。私はプライムビデオで視聴しているので、大抵いくつかの感想がTwitterで目に入ってから見ることになります。そのため、10話の視聴前はかなり不安でした。「これでダメでも残り2話だし、一緒に沈むか?」とか考えていたほど。にも関わらず、見終わった後に思ったことは「これ、まだ大丈夫じゃない?」でした。

で、何で悲観的にならなかったのか、というのが少し整理できたので、「こういう展開への希望を残しておいてほしいな」という希望的妄想を持ってこの2話の感想に変えたいと思います。

9話、10話で何が起こったか

異方少女マジカル沙羅花爆誕。

沙羅花さんは実は異方存在でした。来週からは異世界バトルアニメ「正解するカド」をお楽しみください。とでも言いたげな超展開。そりゃまあ、今までの物語の積み重ね方からしたら「はあ?」ですよ。

しかも沙羅花さんが人類の進歩に作為はいらないという自然派。その理由が「この宇宙のファンだから」とあってもっかい「はあ?」ですよ。ちょっと待って、展開急すぎるのもあるけど、理由とか諸々直球すぎて今までの積み重ねは何だったの?という世界。

10話で3次元に降りてきた異方存在は沙羅花さん一人ではないようなので、これに関する回収があるかどうかは気になるところですが。個人的には品輪博士が名前の語感的に怪しい。ところで「ユノクル」って何ですかね?

真道の交渉はこれからが本番ではないか?という仮説

と、まあ、初見は疑問符がいっぱいあった9話と10話なのですが、それでも見るのをやめるほどには至らなかったわけです。ぼんやりとまだ期待ができる、と思っていたということなんですが、それが10話視聴から1日寝かせてようやくはっきりしてきました。

視点の整理

異方の人類の宇宙への関わり方において、少なくとも二つの視点があることが明らかにされました。

一つは、ザシュニナが寄って立つところで、もっと情報の糸出すようにしてほしいから作為を加えようという視点。これってつまりブロイラーの発想ですよね。人間が家畜や農作物に対して遺伝子操作をする、介入をすることと本質的に変わりありません。その結果、真道がチキンジョージになりそうなので、異方につれて帰ろうとしています。もしかしたらチキンジョージというよりはあれかな、真・女神転生4の赤玉的なアレ。

一方沙羅花さんは、作為はいらない、人類かわいいよ人類という視点。これって一見聞こえばいいんですが、よくよく考えたら、家畜だと思ってたら案外可愛くて、情が移って名前つけたら屠殺できなくなった感覚じゃないかな?とか思ってしまうわけです。ある種の傲慢さを感じさせる視点でもあります。

で、どちらにも共通しているのは、「異方から人類に対してこうあってほしいという希望」であって、「人類が何を選ぶか」というということではないんですよね。ってかメガテンかよ、という感じの両極端さです。現時点では、人類に示された異方からの提案であって、まだ何も選んでいないという状況です。

人類が選択する上で必要な交渉が残っている

で、ここまで整理してようやく、もしかしたら真道が交渉官であるという設定をここから生かすつもりなのかも、と思い至りました。

人類にしてみたら、たとえ作為があろうとも人類を前に進めるという選択はあって良いはずです。まず、ザシュニナと人類という軸はある意味交渉になりません。チキンジョージ計画はともかくとして、発展という点においては利害は最初から一致しているわけですから。じゃあ、人類側の代表に選ばれた日本と世界という軸で考えたとしても、日本と世界の確執を描くはずで、さすがに今までの積み重ね方からしてあまりにも主眼が違いすぎる。ということは、もたらされる二つの両極端な提案から、提案者の利益に配慮しつつ人類が発展の利益最大化する落とし所を見つける交渉をする、というのが今後の真道の役回りになるのではないかと。

0話で示されている通り、彼は請求に交渉の場をセッティングすることはしないタイプです。ということは、今まで彼が異方側にいたのは、0話で視察をしていたことと同じではないのか?その上で、今度は人類の側としてテーブルにつくつもりではないのか?という妄想ができるわけですよ。

もし、そうなれば、ロールートでもカオスルートでもないニュートラルルートの選択を人類がしていくための交渉ということで、ストーリー的にもまだまだ面白いポイントは残ってるんじゃないか、というのを感じますね。

で、ザシュニナさん、とりあえず別ブランチの真道をつれ回るようになりましたね。ということは、もしかして人類の視点から別々の立場で交渉の場に臨む真道vs真道の可能性も?

とりあえず

沈もうが沈むまいが、最後まで乗船しててもいい作品ではないのかな、というのが今の私の感想です。 まあ、提示された作為によって何が変わるのかという描写が軽いという意見もありますが、それは良いんじゃないですかね。大抵それはさらっと地の文で流すことの方が多いですし。(それは個人的な変革体験がある特定の時間帯にまとめて発生したということでしか