権限なぜか無視されてみんな編集できる問題終結

権限周りの一般的な説明はこっち.

tna-system-memo.hatenadiary.com

上の記事にも書いたとおり

編集者権限の中でのセル,シートの保護は,編集者の中でも編集できる人を変更できる.それによって下の授業データだけ保護できるはずであった.

実際に,

保護したい範囲を選択 -> 右クリック -> 範囲を保護

という手順で手動で保護すると保護でき,自分のアカウントで編集しようとすると触れなくなってる.が,スクリプト内でシートを保護する関数を起動してるので,作成された際に元からこの状態になるはずだし,実際に確認するといつもちゃんとその状態になってる.だがみんな編集できるっていう問題があった.(毎月手動でやればって問題もあったんだけど.)

ずっと不思議でごちゃごちゃ触ってたら気付かされた.

f:id:tna-teachers:20181020142555p:plain

上が不思議な状態で右は自分のアカウントで編集,普通に編集できちゃう.

f:id:tna-teachers:20181020142605p:plain

ちゃんと保護されてるよな,っていう確認するところ...

f:id:tna-teachers:20181020142638p:plain

f:id:tna-teachers:20181020142649p:plain

f:id:tna-teachers:20181020142657p:plain

3つの画像の流れからしてもちゃんとされてる,されてるなぁって完了して閉じて,でもなぁ,ってもっかい触ったら,

なんと編集できんくなった. 見た目は開けると保護されてるように見えてたけど完了までしてなかった?手動でそこを開いたら完了した?

てことでスクリプトほんとに完了されてるのかってのを確認したら見つかった.


  //シートを保護
  var MonthSheet = ss.getSheetByName(sheet.getRange("I6").getValue()+"月");
  MonthSheet.protect();

まず,上の記事でも書いたけど編集権限持ってる人しかスクリプト使えないので,Monthsheet全体を保護するとレポート閲覧のボタンすら触れなくなるのでよろしくない.結局効いてないから放置してたけどこのボタン使えなくなるの以外にトリッキーだからみんな気をつけて.

そんでこのスクリプトはこれで終わってしまってるんだけど編集できる人とかを与えてない....

f:id:tna-teachers:20181020144612p:plain

その場合編集権限全員が権限を持ってしまうからこの範囲に対する protection オブジェクトに対しての編集者を追加してそれ以外の編集者権限の人を外す関数を呼び出す必要があるとのこと.

  var protection = MonthSheet.getRange(5, 1, MonthSheet.getLastRow()-5, MonthSheet.getLastColumn()).protect();
  var me = Session.getEffectiveUser();
  protection.addEditor(me);
  protection.removeEditors(protection.getEditors());

実際にとある1つのセルで,

  • 手動で保護
  • 元のコードで保護, からの編集まだできることを確認してから保護されてるかの確認だけの作業をはさんでからの確認
  • 新しいコードで保護

試してみたら解決した.よかった.

生徒管理システム スクリプトの説明

それぞれの用途に関しては使用者向けドキュメントの方を確認.

tna-system-memo.hatenadiary.com

基本的にタイムトリガー,ボタンに依る呼び出しはなく,すべて上部メニューから機能は使われるようになっている.支援員からの報告を受け取って反映する部分のみ,Formからの受信に対して呼び出されるトリガーが付いている.

main system

aboutGmail.gs

全拠点不参加に依る休講の講師への連絡,一拠点不参加のときの講師への連絡(いまはとまっている),保護者へのメール,エラーを把握するための社員と自分へのメールなど.

aboutUI.gs

メニューに機能を追加することと,それぞれの簡単な質問のやり取りが載っている. すべての生成をするときの確認メッセージ,特定の生成する時になに生成するかの質問,生徒の追加をする際のどれに対して行うかの質問.

addStudent.gs

既存の授業の生徒管理システムに生徒を追加する場合(生徒名簿に追加したところでフォームやシステムには反映されない.)に使用するやつ.addStudent_coreがメイン.その中で,名簿への追加,SSへの追加,生徒への追加を行っている.

createSystem.gs

システムの生成を行う.main()がメイン.createManagementoSystemForAllClasses, createManagementSystemForOneClassはその上でそれを用いている感じ.main関数の中にコメントしてあるがその中で,

function main(class_name, meibo_sheet){
    //meibo_sheetから生徒リストの取得. 全てのデータを取得すると保護者アドレスが入っている場合があるので弾く.
    var class_students = meibo_sheet.getDataRange().getValues()
    for (var i=0; i<class_students.length; i++){
      class_students[i] = class_students[i].slice(0, 2)
    }
    
    //同一の授業名が既存でないかのチェック,既存なら上書き仕様.
    resetClass(class_name)

    //①授業名と生徒リストからフォームを作成
    var class_form = createClassForm(class_name, class_students)

    //②フォームをメインシートに紐付ける.紐付けたシート名を授業名にする.
    connectClassForm(class_name, class_form)

    //③授業名と生徒リストからスプレッドシートを作成し,ssidをデータベースに保存しておく
    var class_ss = createClassSS(class_name, class_students)
    
    //(+)フォームの確認メッセージに作成したスプレッドシートのurlを入れる.
    setMessageToForm(class_form, class_ss)
    
    //④teachers_listに,作成した授業名がなければその枠を新たに作成.
    insertToTeachersList(class_name)
}

receiveAbsent.gs

支援員の報告を受け取る.

function receiveAbsent() {
  
  //①フォーム入力によりActiveとなった授業名の取得,受け取ったアイテムの取得
  var class_name = SpreadsheetApp.getActiveSheet().getSheetName()
  var itemResponses = SpreadsheetApp.getActiveRange().getValues()[0]
  
  //②授業名から日付と生徒名リストについて取得
  var DNList = getDateNameList(class_name)
  
  //③欠席者(複数名も含む)の座標を取得
  var coord = getCoord(itemResponses, DNList)
  
  //④欠席者に対して処理.その後メールが必要であれば送信.
  setcheck(coord, class_name)
}

searchTeacher.gs

月,日,拠点,学年教科を用いて授業管理シートから講師を取得し,classシートからアドレスを取得.

students_list (生徒名簿)

授業シート1枚ずつが各授業になっており,生徒が入っている.

aboutUI.gs

生徒管理システムに不具合を起こさないため,授業シートの追加のみシステムで行っており,授業管理シートのclassシートにきちんと該当する授業があるかのチェックを行っている.

form&ss URL自動収集ツール

まとめサイトのために生成された既存のform&ssを抽出してくるツール.

授業管理シート以外のSSファイル

授業管理システムのファイル同士のつながり

tnaの授業管理システムは授業管理シートがほとんどだが,レポートや引継ぎ,リマインダの中でフォームを用いていることでそれぞれにSSがあり連携している.その関係性は以下のような感じ. 基本的に矢印の出発点の場所が,その矢印の機能の持ち主なのでそのへんでトラブル起きたらそのスクリプトエディタを見るようにすると良い.

f:id:tna-teachers:20180916022756p:plain

また,みて分かる通り代講依頼SSの存在意義が意味がわからない.わざわざなぜ一旦違うファイルを介するのか.

なので簡単に整理してから引き継ぎしたい.が,代講は大事なところなので時間のある時に丁寧にやる.

全プログラムファイルの置き場所は以下,

https://drive.google.com/drive/folders/1vb5N7KJouKMxq-08MiU2wILCARAcwvk9

レポートSS

  • ファイル名「TNA: 指導報告書(回答)」
  • 指導報告をGoogle Formで受けて溜まっていく.

updateDailyReport

指導報告を受けた時に授業管理シートを反映

sendEmailAltReport

指導報告を受けた時に代講であった場合,代講報告のメールを送信.

引継ぎSS

  • ファイル名「代講引継ぎのフォーム(回答)」
  • 代講引継ぎをGoogle Formで受けて溜まっていく.

sendEmailAltTakeOver

引き継ぎを受けた際に,メールを送信して授業管理シートを反映.

リマインダーSS

  • ファイル名「授業確認フォーム(回答)」
  • 朝の授業確認をGoogle Formで受けて溜まっていく.

confirmClassOfDay

授業管理シート内の授業確認を「完了」に

confirmClassOffDcr

授業管理シート内の授業確認を「休講」に

confirmClassCheck

授業確認が取れていない授業の一覧を担当者(現在は岡崎)に通知.

confirmClassCheckHoliday

授業確認が取れていない授業の一覧を担当者(現在は岡崎)に通知.休日用.

代講依頼SS

  • ファイル名「代講依頼履歴」

授業管理シートの代講申請は実際はこれに代講依頼を付け加えているだけ,実際はこのSSが代講のセッティングを行っている(謎の機構)

altWrite

授業管理シートに代講依頼を転記する.

生徒管理システム 使用者向けドキュメント

1. 概要

生徒の無断欠席ないしは授業全体の直前の休講を防ぐ目的(最終的には生徒の欠席をなるべく防ぐ目的)に,生徒全員の出欠を管理するためのシステムです.

  • 各支援員さんに出欠を登録していただきます.
  • 講師みんなが自分の授業の生徒みんなの出欠を把握できるようにします.
  • また,生徒の欠席が揃い拠点全体が休講となった場合,該当授業の講師に休講連絡が行くようにします.
  • また,生徒の欠席届があった時,保護者の方にメールが届くようにします.

支援員さんの登録

  • 生徒の欠席が出たとき,各支援員さんは Googleフォームを使用して生徒の欠席を報告します.
  • Googleフォームから報告されたものが1つのデータベースに集まり,プログラムによってそれぞれの授業のスプレッドシートの該当の生徒の該当の日付けのところに反映されます.
    • スプレッドシートに直接欠席を記入しないのは,スプレッドシートを操作できない支援員さんの方がいらっしゃるためです.全ての支援員さんにとって優しい Googleフォームによる報告に致しました.
  • Googleフォームは全ての授業のためにそれぞれ用意されています.
  • 反映するスプレッドシートは全ての授業のためにそれぞれ用意されています.

f:id:tna-teachers:20180916020311p:plain

URLまとめサイトの存在

  • 全授業のそれぞれの Googleフォーム(支援員さんが出欠を報告するために使用するもの),それぞれのスプレッドシート(生徒の欠席を反映する閲覧用のもの)は,1つのサイトにまとめておきます.

f:id:tna-teachers:20180916020344p:plain

2. システム使用方法 (授業の追加・生徒の追加)

年度の変わり目に全授業ぶん上のようなシステムを作ったり,授業が新しく増えたときに追加したり生徒を新たに加えたりってことですね.

元々プログラムとかファイルは作ってあるのでそれらを使って授業の追加とかを以下のようにお願いします.

使用するファイル一覧

新しいシステムのファイルはここにあります.

https://drive.google.com/drive/folders/1VsO7WXXb_7GfBRtJaklBBGXR-R1p604O

f:id:tna-teachers:20180916030059p:plain

  • template: 授業ごとにフォーム,シートを作成するためのテンプレートを保存しているフォルダ.
  • form&ss: 授業ごとに作成されるフォーム,シートを保存するフォルダ.
  • students_list: 生徒名簿.
  • main_system: 支援員さんからの連絡を受け取ったり,システムの最初の構築を行ったりシステムのほとんどが実装されている大事なやつ.
  • form&ss URL自動収集ツール: カレンダーを手作業で作成するときにURLを全て調べるのがめんどくさいんで自動でURLだけ収集するツールを作りました.ご使用ください.

2-1. 授業の追加

まず,授業の追加についてです.最初にまとめて授業を追加する場合,新規に1つずつ授業を追加する場合にご使用ください.

f:id:tna-teachers:20180916020443p:plain

1.生徒名簿入力!

f:id:tna-teachers:20180916020457p:plain

生徒名簿(students_list)に授業ごとに生徒を入力してください.

  1. 上メニューにある「授業シートの追加」から授業のためのシートを追加してください.
    • 授業名は授業管理シートの「class」シートを確認しながら「(拠点名)_(学年教科)」となるようにしてください.そうすることで授業管理シートとリンクするようになっています.
    • 英数字は半角にしてください.また,授業管理シートに該当の授業名がない場合,作成できないようにしてあります.
  2. シートが追加されたら,一行ごとに左から「拠点名,生徒名,(必要な人のみ)保護者のメールアドレス」となるように生徒を入力してください.

2.生成ボタンをクリック!

main_systemの上メニューにある「生徒管理システム」をクリック.該当の選択肢をクリック!

  • 「生徒名簿から全ての授業のシステムを生成」ボタン: 最初にまとめて授業を追加するときにご使用ください.生徒名簿にある全ての授業に関してシステムを生成します.

  • 「生徒名簿から特定の授業のシステムを生成」ボタン: 授業を新規に追加するときにご使用ください.追加する授業名を入力し,特定の授業に関してシステムを生成します.

f:id:tna-teachers:20180916020616p:plain

3.日付け入力!

f:id:tna-teachers:20180916020625p:plain

シートは生成されました,がしかし授業によって授業開始日が異なるので日付けは記入されていません.

授業の日付けの記入だけお願いします.

4.まとめサイト編集!

f:id:tna-teachers:20180916020639p:plain

最後に閲覧用のまとめサイトにURLを打ち込みましょう.

form&ss URL自動収集ツールぜひご使用くださーい.見たら使い方わかります.

以上で完成です!

2-2. 生徒の追加

次に,生徒の追加についてです.既に生成した授業について新たに生徒を追加する際にご使用ください.

1.生徒の追加ボタンをクリック!

main_system の上メニューにある「生徒管理システム」の「生徒の追加」をクリック!

f:id:tna-teachers:20180916020704p:plain

2.質問に答える!

f:id:tna-teachers:20180916020716p:plain

その後,右画像のように質問が出てくるので追加したい授業名,拠点名,生徒名を質問に従って順番に答えてあげるだけです.

以上で追加完了です!

3. システムの挙動の簡易的説明

エラーなどを探すために内容を知っていると助けになると思うので,支援員さんから欠席報告を受けた時にシステムが実際にどういう挙動をしているかの簡単な説明を載せておきます.イメージ図は"1.概要"にあります.

  1. 支援員さんがGoogle フォームを用いて欠席を報告.
  2. main_systemに内容が届きます.(システム生成の際に main_systemに届くように紐づけされています.)
  3. どのGoogleフォームから来たかを判断し,対応するスプレッドシートに接続します.(システム生成の際に全てのスプレッドシートをデータベースに登録してあります.)
  4. 支援員さんの登録した日付け・生徒名から,該当する枠を検索し,「欠席」を入力して背景を黄色にします.(なので日付けがスプレッドシートに登録されていなければもちろん反映されません.)
  5. 授業名,生徒名から students_list を検索し,保護者のアドレスが登録されていればメールを生成して送信します.
  6. 欠席が登録された日程について全生徒の欠席を確認して授業が休講となった場合,担当講師に休講のメールを生成して送信します.その際,授業名と日付けから授業管理シートよりその授業を担当している講師を検索し,各講師に登録されているアドレスを使用します.(全体の休講だけでなく,拠点ごとの不参加についても判断していますが,現在はメールの送信を止めています.)

権限まわり

共有の際の権限の種類

  • 編集者
  • コメント可
  • 閲覧者

この際,スクリプトの使用ができるのが編集者のみであることは確認済み.そのためみんなを閲覧権限のみにすると機能を使用できなくなる.

ファイルを開けた瞬間に走るプログラムも走らないため,上に追加される経理,講師,社員,などのメニューもそもそも存在しなくなる.

ので編集者権限であることは必須となる.(それすらもサイトで代替してスタッフ権限以外完全なる閲覧用にしようともしている.

編集者権限の中でのセル,シートの保護

編集者の中でも編集できる人を変更できる.

この機能によってシートを保護しているつもりになっているのになぜか全員編集できてしまって困っているという問題.

(2018.10)解決した

tna-system-memo.hatenadiary.com

デバッグの基本的な注意

エラーが有ってそれを解決するためにエラーの場所を探す時の注意,あるいは新しい機能を作成する時の注意

MailApp.sendEmail(mainto,offheader+mainMailHeader,mainMailBody);//レギュラー講師に授業通知

ってところがあったら,コメントアウトしてログを出力する文に置き換える

// MailApp.sendEmail(mainto,offheader+mainMailHeader,mainMailBody);//レギュラー講師に授業通知
Logger.log('レギュラー講師に授業通知')
Logger.log([mainto,offheader+mainMailHeader,mainMailBody]);//レギュラー講師に授業通知

補足

Logger.log() でログを出力する.

出力すると,他の何かを実行するまで,ログのボードにログが出力される.ボードは command + Enterで表示される.

f:id:tna-teachers:20180905160649p:plain

スクリプト,スプレッドシートの制限

スクリプトgmailをアホみたいに出しすぎると制限にかかるのでそれも載せておく.僕の一個前の代で実際にかかったことがある (それでangryとかreminderとかのアカウントが分かれてる)

Quotas for Google Services  |  Apps Script  |  Google Developers

また,スプレッドシートのファイルサイズの上限として合計20万セルってものがある.生徒管理システムのときに実際にかかったことがある

数字を覚えておく必要があるというよりかは,そういう制限があるんだってことを頭に入れておいてほしい.