GASでExcelと連携したモバイルアプリを作った

# 今回やりたかったこと(いきさつ)
親：なんかこの業務楽にしたいからアプリ作ってくれない？
私：エエで、どんなん？
親：なんか商品を検索できるやつ。
私：ああ、なんや。(そんなに難しそうじゃないな)とりあえず要件聞こうか？
親：このExcelからデータ検索してそれを出してほしいんだけど
私：ふぁー？

# 今回書くこと
GASを用いて簡易Webアプリを作った時の備忘録です。以下のような人には参考になると思います。
- GASを使ってみたい。
- 簡易Webアプリを作ってみたい
- GASを使うためのテクニックを知りたい

# いきさつからいろいろと考えたこと  

- アプリ作るならマルチプラットフォーム(どこでも動くやつ)がええよな
    - Web公開ならHTTPSでやりたい
- できれば短めの終わらせたいね、4時間ぐらいで
- (自分が使ったことのない)新しい技術使ってみたいね

***⇒そうだ。GASを使おう***

# GASとは
正式名はGoogle Apps Script。
GoogleのOfficeっぽい製品(Google Document,Spread Sheet等)をプログラムを通して扱えたりする。
要はOfficeのマクロ的なもの。
ポイントとしては、Office関連のソフト(ExcelやWord等)は、Googleのアプリ形式(DocumentやSpreadSheet等)に
落としこむことができるので、連携が可能。身近な業務のWebを用いた自動化などに一役買ってくれるかも。

# 必要なこと
- googleアカウント
- googleドライブと拡張
    - 右クリックで「アプリを追加」をクリック⇒Google Apps Scriptを検索、選択(下の図)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/141369/e8ea70d8-b84a-ad7c-e555-8a15f29429e7.png)

# GASにできること
- 一定の時間になったら関数(自動処理など)を起動する
- REST APIチックな使い方をする
- HTMLを書いてウェブアプリとして公開する

# 実際に作ってみよう

## ベースとなるシートを用意する

~~作り方めっちゃわかりにくいんだけど~~
用意方法は２種類

- スプレッドシードなどから
- Google Driveで右クリックで、その中にあるGoogle Apps Scriptをクリック

## プログラムを書く
後は実際に書いてみる！
書き方は基本的にJavaScript

```
function test(){
 var test = "hogehoge"
}
```

## 今回のアプリを使うにあたって必要だった知識

### SpreadSheetとの連携コード

```
var spreadsheet = SpreadsheetApp.openById(識別ID);　// 識別IDはspreadSheetを開いた時に/d/の次にある文字列
var sheet = spreadsheet.getSheetByName(シート名);
var date = sheet.getDataRange().getValues(); //受け取ったシートのデータを二次元配列に取得
```

### HTMLとの連携

#### HTMLの開き方
ファイル > NEW > HTMLファイル
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/141369/eaa83777-d1aa-b9cf-ef7e-c3b1fbe3d8e1.png)

#### HTMLの書き方
普通に書けば良い。
外部リソース(インターネット上のCDN等)なども読み込み可能。
ただし、自作のスクリプト(外だししたJavaScript等)を埋め込むときには注意が必要。
また、metaタグなどをこのファイルに記述しても読み込んだ際に無視されてしまうので、注意が必要(対応策は後述)

#### 外部スクリプト
プロジェクトファイルとして登録できるのはスクリプトファイル(.gs)とHTMLファイル(.html)だけなので、一見CSSやJavaScriptファイルを自分で分割することができないように見える。ここには少し工夫が必要
まずは外出ししたいファイルをHTMLとして記述する。
要は`<script>`タグや`<style type="text/css">`タグだけのHTMLファイルを記述する
そのあと、読み込みたい元のファイルでGASの組み込み関数である
`<?!= HtmlService.createHtmlOutputFromFile(ファイル名).getContent(); ?>`
を記述する。**ファイル名にいれるのは拡張子を除いたものであるのに注意**

#### GAS側から値を埋め込む
サーバープログラム側から値を埋め込みたいときは、変数を埋め込みたいところに`<?=変数名?>`を記述しておく。

#### 補足説明
この'<?!= ?>' で囲まれた部分は後ほど紹介するスクリプトからHTMLを読み込む際に、スクリプトとして解釈される部分です。なので今回はHTMLを読み込むスクリプトをHTML内部から読み込んで、疑似的に外だしファイルを実現しています。


### サーバーとしての関数、変数
ページとして公開した際にアクセスされた際に必要な関数の紹介をします。
GETとPOSTそれぞれであるので注意

#### GET
```
function doGet(e){
 //GET時の処理を記述する
　return HTMLファイル(後述)
}
```

#### POST

```
function doPost(e){
 //GET時の処理を記述する
 return HTMLファイル(後述)
}
```

#### GETやPOST関数の引数　e
このeは便利な機能がいくつかあり、ヘッダー情報はボディ情報などが保持されている。
今回使ったのはパラメーターを取得する際の機能を使用した
例えば、`https://script.google.com/macros/s/hogehoge/exec?id=test`でアクセスした場合、以下で取得できる
`var id = e.parameter.id`
POSTの際も取得の仕方は同様

#### HTMLファイルの読み込み方
関数の中で以下のGS組み込み関数で取得
`var html = HtmlService.createTemplateFromFile(ファイル名);`
ファイル名のところは拡張子を付けない点に注意。htmlを作成する際にサーバーから埋め込みたい値は変数としてアクセス可能
`html.HTMLに組み込んだ変数`
また、上の組み込み関数で読み込んだファイルはレンダリングをしなければならず、以下の関数で実行可能。
そして***この評価する際にmetaタグやタイトル等の情報も埋め込む点に注意。例えばモバイル対応も行うならmetaタグにviewport width=device-widthを入れておかないと表示が崩れる等である。***

```
html.evaluate();//htmlを評価して、読み込んだhtmlファイルに含まれているgasの関数なども処理する
html.setTitle("testPage");//タイトルを定める
html.addMetaTag('viewport', 'width=device-width, initial-scale=1');//メタタグ等の設定も行う
```
ちなみに上記関数はメソッドチェーン的につなぐことも可能

## 付録：パラメーターを取得してそれをそのまま表示するプログラム

```gas.gs
function doGet(e){
  var param = "";
  if(e.parameter.param == undefined){
    param = e.parameter.param
  }
  var html = HtmlService.createTemplateFromFile('index');
  html.param = param
  return html.evaluate().setTitle("test").addMetaTag('viewport', 'width=device-width, initial-scale=1');
}
```

```html:index.html
<!DOCTYPE html>
<html>
  <head>
    <base target="_top">
  </head>
  <body>
    <h1>テストページ</h1>
    <form action="" method="GET">
        <legend for="testparam">コードを入力</legend>
        <input type="text" name="param" id="testparam">
        <input type="submit" value="送信">
    </form>
    <h1>パラメーター</h1>
    <div><?=param?></div>
    
  </body>
</html>
```

## 公開
上記タブの中の
公開 > ウェブアプリケーションとして導入 > 別ウィンドウ下部にある公開をクリック
この際にgoogleアカウントの認証を求められるが、承認を行う。
ここで出ているCurrent web app URLは変更されることがないので、getやpostなどのURLは特に変更する必要はない(はず…)

# 感想
思ったより簡単にwebappを構築することはできたが、
モバイル対応を行うのにそこそこ手間取った記憶はある(metaタグが使えなかったのが原因を探すのに苦労した)
今後も手軽にアプリを開発する手法として覚えておきたい。